Files
darkfi/script/research/blockchain-explorer/site/blueprints/explore.py
kalm c58fd56041 explorer: native contract source code UI
This commit introduces functionality for displaying native contract source code in the DarkFi explorer application, enabling users to view available contracts from the home page, access associated source files, and examine native contract Rust code and zk proofs. This enhancement provides accessibility to native contract information. To support these updates, we have added new pages to the UI, updated styles for rendering source-related pages, and implemented new RPC routes to facilitate contract-related code retrieval.

Additionally, we have restructured the application into Flask blueprints to address the growing complexity of the explorer and adhere to best practices, as app.py was becoming large with diverging functionality. This proactive change prepares us for future expansions, including better organization of graph functionalities. The organization also mirrors the rest of the explorer codebase by maintaining separate pages for contracts, transactions, and blocks, as well as corresponding RPC and service rust modules.

UI Support for Native Contract Source Code

- We have added source code functionality to the UI, Flask blueprints, and RPC routes defined in rpc.py, along with updated styles to effectively render source-related pages.

Style Updates:
- Expanded the color palette for rendering source files.
- Enhanced styles for displaying contract IDs and names in the native contracts table.
- Implemented layout elements for proper display of source code lists and content.
- Added styles for source file list links, including hover effects.

RPC Routes:
- New routes have been added to facilitate requests to the DarkFi daemon for retrieving native contracts, source code paths, and contract source.

UI Enhancements:
- A native contract section has been introduced on the explorer home page to display native contracts.
- A contract source list page allows users to view and click on source code files associated with a native contract.
- A dedicated contract source page renders the source for a specific path associated with a given contract.

Introducing Flask Blueprints

To better manage the growing complexity of the application, we introduced Flask blueprints that organize routes according to their functionality. This restructuring not only enhances readability but also aligns with best practices for Flask applications, facilitating future development.

App.py Updates:
- Routes have been moved to their respective blueprints.

Added Blueprints:
- `__init__.py` file initializes the explorer blueprint package and exposes various blueprints used by the application.
- `block.py` module defines a blueprint for handling block-related functionality.
- `contract.py` module defines a blueprint for managing contract-related functionality.
- explore.py` module manages general functionality related to the home page and search features.
- `transaction.py` module handles transaction-related functionality.

Python Documentation:

- We documented the Python code and updated existing documentation to adhere to Python's best practices for using docstrings, enhancing usability and integration with documentation tools.

Testing:

- Manual testing has been conducted through the UI to verify the functionality of the new RPC methods, ensuring they correctly retrieve and display contract-related information.
2025-01-15 14:21:24 -08:00

94 lines
3.6 KiB
Python

# This file is part of DarkFi (https://dark.fi)
#
# Copyright (C) 2020-2024 Dyne.org foundation
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU Affero General Public License as
# published by the Free Software Foundation, either version 3 of the
# License, or (at your option) any later version.
#
# This program 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 Affero General Public License for more details.
#
# You should have received a copy of the GNU Affero General Public License
# along with this program. If not, see <https://www.gnu.org/licenses/>.
"""
Blueprint: explorer_bp
This module defines a Flask blueprint (`explore_bp`) for managing the general functionality of the explorer application.
It serves as the primary location for Flask routes related to the home page, search functionality, and other general features.
"""
from flask import Blueprint, render_template, request
import rpc
# Create explore blueprint
explore_bp = Blueprint("explore", __name__)
@explore_bp.route('/', methods=["GET"])
async def index():
"""
Fetches and displays the explorer home page content using multiple RPC calls to the
explorer daemon, retrieving the last 10 blocks, basic statistics, metric statistics,
and DarkFi native contracts.
Upon success, it returns a rendered template with recent blocks, basic statistics,
latest metric statistics (if available), and native contracts.
"""
# Fetch the latest 10 blocks
blocks = await rpc.get_last_n_blocks("10")
# Retrieve basic statistics summarizing the overall chain data
basic_stats = await rpc.get_basic_statistics()
# Fetch the metric statistics
metric_stats = await rpc.get_metric_statistics()
# Determine if metrics exist
has_metrics = metric_stats and isinstance(metric_stats, list)
# Get the latest metric statistics or set to None if none are found
latest_metric_stats = metric_stats[-1] if has_metrics else None
# Retrieve the native contracts
native_contracts = await rpc.get_native_contracts()
# Render the explorer home page
return render_template(
'index.html',
blocks=blocks,
basic_stats=basic_stats,
metric_stats=latest_metric_stats,
native_contracts=native_contracts,
)
@explore_bp.route('/search', methods=['GET', 'POST'])
async def search():
"""
Searches for a block or transaction based on the provided hash using RPC calls to the
explorer daemon. It retrieves relevant data using the search hash from provided query parameter,
returning a rendered template that displays either block details with associated transactions
or transaction details, depending on the search result.
Query Params:
search_hash (str): The hash of the block or transaction to search for.
"""
# Get the search hash
search_hash = request.args.get('search_hash', '')
# Fetch the block corresponding to the search hash
block = await rpc.get_block(search_hash)
# Fetch transactions associated with the block
transactions = await rpc.get_block_transactions(search_hash)
if transactions:
# Render block details with associated transactions if found
return render_template('block.html', block=block, transactions=transactions)
else:
# Fetch transaction details if no transactions are found for the block
transaction = await rpc.get_transaction(search_hash)
return render_template('transaction.html', transaction=transaction)