from os import path from secrets import token_urlsafe from json import loads, dumps import ipfsApi from flask import Blueprint, render_template, request, current_app from flask import send_from_directory, redirect, flash, url_for from requests.exceptions import HTTPError from web3 import Web3 from suchwowx.models import Meme from suchwowx.factory import db from suchwowx import config bp = Blueprint('meta', 'meta') @bp.route('/') def index(): memes = Meme.query.filter().order_by(Meme.create_date.desc()) w3 = Web3(Web3.HTTPProvider('http://127.0.0.1:9650')) contract_address = w3.toChecksumAddress(config.CONTRACT_ADDRESS) contract_abi = config.CONTRACT_ABI contract = w3.eth.contract( address=contract_address, abi=contract_abi ) # total_supply = contract.functions.totalSupply().call() return render_template('index.html', memes=memes, contract=contract) @bp.route('/about') def about(): return render_template('about.html') @bp.route('/new', methods=['GET', 'POST']) def new(): meme = None form_err = False try: client = ipfsApi.Client('127.0.0.1', 5001) client.add_json({}) except Exception as e: msg = f'[!] IPFS Error: {e}' print(msg) flash(msg, 'error') if "file" in request.files: return '' return redirect(url_for('meta.index')) if "file" in request.files: if form_err: return '' title = request.form.get('title') description = request.form.get('description') creator = request.form.get('creator') file = request.files["file"] filename = "{}{}".format( token_urlsafe(24), path.splitext(file.filename)[1] ) full_path = f'{config.DATA_FOLDER}/uploads/{filename}' file.save(full_path) try: client = ipfsApi.Client('127.0.0.1', 5001) artwork_hashes = client.add(full_path) print(artwork_hashes) artwork_hash = artwork_hashes[0]['Hash'] print(artwork_hash) # client.pin_add(artwork_hash) print(f'[+] Uploaded artwork to IPFS: {artwork_hash}') # Create meta json meta = { 'name': title, 'description': description, 'image': f'ipfs://{artwork_hash}', 'by': creator, 'properties': { 'creator': creator } } meta_hash = client.add_json(meta) # client.pin_add(meta_hash) print(f'[+] Uploaded metadata to IPFS: {meta_hash}') meme = Meme( upload_path=filename, meta_ipfs_hash=meta_hash, meme_ipfs_hash=artwork_hash, title=title, description=description, creator_handle=creator ) db.session.add(meme) db.session.commit() return redirect('/') except ConnectionError: flash('[!] Unable to connect to local ipfs', 'error') except Exception as e: print(e) return render_template( 'new.html', meme=meme ) @bp.route('/uploads/') def uploaded_file(filename): """ Retrieve an uploaded file from uploads directory. """ return send_from_directory(f'{config.DATA_FOLDER}/uploads', filename) @bp.route('/meme/') def meme(meme_id): meme = Meme.query.filter(Meme.id == meme_id).first() if not meme: return redirect('/') return render_template('meme.html', meme=meme) @bp.route('/creator/') def creator(handle): return render_template('includes/creator.html')