Äú¿ÉÒÔ¾èÖú£¬Ö§³ÖÎÒÃǵĹ«ÒæÊÂÒµ¡£

1Ôª 10Ôª 50Ôª





ÈÏÖ¤Â룺  ÑéÖ¤Âë,¿´²»Çå³þ?Çëµã»÷Ë¢ÐÂÑéÖ¤Âë ±ØÌî



  ÇóÖª ÎÄÕ ÎÄ¿â Lib ÊÓÆµ iPerson ¿Î³Ì ÈÏÖ¤ ×Éѯ ¹¤¾ß ½²×ù Model Center   Code  
»áÔ±   
   
 
     
   
 ¶©ÔÄ
  ¾èÖú
ʹÓà Python ´ÓÁ㿪ʼ¿ª·¢Çø¿éÁ´Ó¦ÓóÌÐò
 
  2478  次浏览      31
 2018-5-25 
 
±à¼­ÍƼö:
À´Ô´IBM£¬±¾½Ì³Ì½«Ïò¾ßÓÐÈκαà³Ì¼¼ÄÜˮƽµÄ Python ¿ª·¢ÈËÔ±½éÉÜÇø¿éÁ´¡£Í¨¹ý´ÓÁ㿪ʼʵÏÖÒ»¸ö¹«ÓÐÇø¿éÁ´²¢¹¹½¨Ò»¸ö¼òµ¥Ó¦ÓóÌÐòÀ´ÀûÓÃËü£¬Äú½«Á˽âÇø¿éÁ´µ½µ×ÊÇʲô¡£

Äú½«Äܹ»Ê¹Óà Flask ΢¿ò¼ÜÎªÇø¿éÁ´µÄ²»Í¬¹¦ÄÜ´´½¨¶Ëµã£¬±ÈÈçÌí¼ÓÊÂÎñ£¬È»ºóÔÚ¶à¸ö»úÆ÷ÉÏÔËÐнű¾À´´´½¨Ò»¸öÈ¥ÖÐÐÄ»¯ÍøÂç¡£Äú»¹½«Á˽âÈçºÎ¹¹½¨Ò»¸ö¼òµ¥µÄÓû§½çÃæ£¬ÒÔ±ãÓëÇø¿éÁ´½øÐн»»¥£¬²¢´æ´¢ÈκÎÓÃÀýµÄÐÅÏ¢£¬±ÈÈç¶ÔµÈÖ§¸¶¡¢ÁÄÌì»òµç×ÓÉÌÎñ¡£

Python ÊÇÒ»ÖÖÈÝÒ×Àí½âµÄ±à³ÌÓïÑÔ£¬ÕâÊÇÎÒÔÚ±¾½Ì³ÌÖÐÑ¡ÔñËüµÄÔ­Òò¡£Í¨¹ýѧϰ±¾½Ì³Ì£¬Äú½«ÊµÏÖÒ»¸ö¹«ÓÐÇø¿éÁ´²¢Á˽âËüµÄʵ¼ÊÓ¦Óá£GitHub ÉÏÌṩÁËÒ»¸öÍêÕûµÄÑù±¾Ó¦ÓóÌÐò´úÂ룬¸ÃÓ¦ÓóÌÐòÍêÈ«ÊÇÓà Python ±àдµÄ¡£

»ñÈ¡´úÂë

Ö÷ÒªÂß¼­°üº¬ÔÚ views.py ÎļþÖС£ÈÃÎÒÃÇÒ»Æð·ÖÎöһϸÃÂß¼­£¬ÒÔ±ãÕæÕýÈ«ÃæÁ˽âÇø¿éÁ´¡£

ǰÌáÌõ¼þ

Python µÄ»ù´¡±à³Ì֪ʶ

Flask ΢¿ò¼Ü£¨ÓÃÓÚ´´½¨Çø¿éÁ´·þÎñÆ÷µÄ¶Ëµã£©

±³¾°

2008 Ä꣬һ¸öÃû½Ð Satoshi Nakamoto µÄÈË£¨»òÕß¿ÉÄÜÊÇÒ»¸öС×飩·¢±íÁËһƪÃûΪ¡¶±ÈÌØ±Ò£ºÒ»ÖֶԵȵç×ÓÏÖ½ðϵͳ¡·µÄ°×ƤÊé¡£¸ÃÎÄÕ½áºÏÁËÃÜÂëѧ¼¼ÊõºÍ¶ÔµÈÍøÂ磬²»ÐèÒªÒÀ¿¿ÖÐÐÄ»¯È¨Íþ»ú¹¹£¨±ÈÈçÒøÐУ©¾ÍÄÜÔÚÈËÃÇÖ®¼äʵÏÖ¸¶¿î¡£±ÈÌØ±ÒÓ¦Ô˶øÉú¡£³ýÁ˱ÈÌØ±ÒÖ®Í⣬ÕâÆªÎÄÕ»¹½éÉÜÁËÒ»ÖÖ´æ´¢Êý¾ÝµÄ·Ö²¼Ê½ÏµÍ³£¨¼´ÏÖÔÚ¹ãΪÈËÖªµÄ¡°Çø¿éÁ´¡±£©£¬¸ÃϵͳµÄÊÊÓ÷¶Î§Ô¶²»Ö»ÊǸ¶¿î»ò¼ÓÃÜ»õ±Ò¡£

´ÓÄÇʱÆð£¬¼¸ºõÿ¸öÐÐÒµ¶¼¶ÔÇø¿éÁ´²úÉúÁËŨºñµÄÐËȤ¡£ÎÞÂÛÊÇÏñ±ÈÌØ±ÒÕâÑùµÄÍêÈ«Êý×Ö»¯µÄ»õ±Ò¡¢ÏñÒÔÌ«·»ÕâÑùµÄ·Ö²¼Ê½¼ÆËã¼¼Êõ£¬»¹ÊÇÏñ IBM Blockchain Platform Ëù»ùÓÚµÄ Hyperledger Fabric ÕâÑùµÄ¿ªÔ´¿ò¼Ü£¬ÏÖÔÚ¶¼ÒÔÇø¿éÁ´×÷ΪÆä±³ºóµÄ»ù´¡¼¼Êõ¡£

¡°Çø¿éÁ´¡±ÊÇʲô£¿

Çø¿éÁ´ÊÇÒ»ÖÖ´æ´¢Êý×ÖÊý¾ÝµÄ·½Ê½¡£Êý¾Ý¿ÉÒÔÊÇÈκÎÄÚÈÝ¡£¶ÔÓÚ±ÈÌØ±Ò£¬ËüÊÇÊÂÎñ£¨ÔÚÕÊ»§Ö®¼ä×ªÒÆ±ÈÌØ±Ò£©£¬ËüÉõÖÁ¿ÉÒÔÊÇÎļþ£»Õâ¶¼Î޹ؽôÒª¡£Êý¾ÝÊÇÒÔÇø¿éÐÎʽ½øÐд洢µÄ£¬Çø¿éʹÓùþÏ£ÖµÁ´½ÓÔÚÒ»Æð¡£Òò´ËµÃÃû¡°Çø¿éÁ´¡±¡£

Çø¿éÁ´µÄÉñÆæÖ®´¦ÊÇÔÚÆäÖÐÌí¼ÓºÍ´æ´¢´ËÀàÊý¾ÝµÄ·½Ê½£¬¸Ã·½Ê½Ôì¾ÍÁËһЩ·Ç³£ÀíÏëµÄÌØÕ÷£º

ÀúÊ·¼Ç¼ÎÞ·¨¸ü¸Ä

ϵͳÎÞ·¨¹¥ÆÆ

Êý¾ÝµÄ³Ö¾Ã±£´æ

ûÓе¥µã¹ÊÕÏ

ÄÇÃ´Çø¿éÁ´ÈçºÎÄܹ»ÊµÏÖÕâÐ©ÌØÕ÷ÄØ£¿ÎÒÃǽ«Í¨¹ýʵÏÖÒ»¸öÇø¿éÁ´À´ÉîÈëÆÊÎöËü¡£ÈÃÎÒÃÇ¿ªÊ¼°É¡£

¹ØÓÚ¸ÃÓ¦ÓóÌÐò

Ê×Ïȶ¨ÒåÒ»ÏÂÎÒÃǽ«Òª¹¹½¨µÄÓ¦ÓóÌÐòµÄÓÃ;¡£ÎÒÃǵÄÄ¿µÄÊǹ¹½¨Ò»¸öÔÊÐíÓû§¹²ÏíÐÅÏ¢µÄ¼òµ¥ÍøÕ¾¡£ÒòΪÄÚÈݽ«´æ´¢ÔÚÇø¿éÁ´ÖУ¬ËùÒÔËüÎÞ·¨¸ü¸ÄÇÒ»áÓÀÔ¶´æÔÚ¡£

ÎÒÃǽ«²ÉÓÃ×Ô϶øÉϵÄʵÏÖ·½Ê½¡£Ê×Ïȶ¨ÒåÎÒÃǽ«´æ´¢ÔÚÇø¿éÁ´ÖеÄÊý¾ÝµÄ½á¹¹¡£ һƪÌû×Ó£¨ÈκÎÓû§ÔÚÎÒÃǵÄÓ¦ÓóÌÐòÉÏ·¢²¼µÄÒ»ÌõÏûÏ¢£©½«ÓÉ 3 ¸ö»ù±¾ÒªËØÀ´±êʶ£º

.1ÄÚÈÝ

2.×÷Õß

3.ʱ¼ä´Á

½«ÊÂÎñ´æ´¢µ½Çø¿éÖÐ

ÎÒÃǽ«²ÉÓÃÒ»Öֹ㷺ʹÓõĸñʽÀ´½«Êý¾Ý´æ´¢ÔÚÇø¿éÁ´ÖУºJSON¡£ÒÔÏÂÊÇһƪ´æ´¢ÔÚÇø¿éÁ´ÖеÄÌû×ӵĸñʽ£º

{
"author": "some_author_name",
"content": "Some thoughts that author wants to share",
"timestamp": "The time at which the content was created"
}

ÊõÓï¡°Êý¾Ý¡±Í¨³£ÔÚ»¥ÁªÍøÉϱ»¡°ÊÂÎñ¡±Ò»´ÊËùÈ¡´ú¡£ËùÒÔ£¬ÎªÁ˱ÜÃâ»ìÏý²¢±£³ÖÒ»Ö£¬ÎÒÃǽ«Ê¹ÓÃÊõÓï¡°ÊÂÎñ¡±À´±íʾÔÚÎÒÃǵÄʾÀýÓ¦ÓóÌÐòÖз¢²¼µÄÊý¾Ý¡£

ÊÂÎñ±»´ò°üµ½Çø¿éÖС£Ò»¸öÇø¿é¿ÉÒÔ°üº¬Ò»¸ö»òÐí¶à¸öÊÂÎñ¡£°üº¬ÊÂÎñµÄÇø¿éƵ·±µØÉú³É²¢Ìí¼Óµ½Çø¿éÁ´ÖС£ÒòΪ¿ÉÄÜÓжà¸öÇø¿é£¬ËùÒÔÿ¸öÇø¿é¶¼Ó¦ÓÐÒ»¸öΨһ ID£º

class Block:
def __init__(self, index, transactions, timestamp):
self.index = []
self.transactions = transactions
self.timestamp = timestamp

ÈÃÇø¿é²»¿É¸ü¸Ä

ÎÒÃÇÏ£Íû¼ì²â³ö¶ÔÇø¿éÄÚ´æ´¢µÄÊý¾ÝµÄÈκδ۸ġ£ÔÚÇø¿éÁ´ÖУ¬ÕâÊÇʹÓÃÒ»¸ö¹þÏ£º¯ÊýÀ´ÊµÏֵġ£

¹þÏ£º¯Êý½ÓÊÜÈκδóСµÄÊý¾Ý²¢Éú³É¹Ì¶¨´óСµÄÊý¾Ý£¬¸Ã½á¹ûͨ³£ÓÃÓÚʶ±ðÊäÈë¡£ÏÂÃæÊÇ Python ÖеÄÒ»¸öʹÓà sha256 ¹þÏ£º¯ÊýµÄʾÀý£º

>>> from hashlib import sha256
>>> data = "Some variable length data"
>>> sha256(data).hexdigest()
'b919fbbcae38e2bdaebb6c04ed4098e5c 70563d2dc51e085f784c058ff208516'
>>> sha256(data).hexdigest() # no matter how many times you run it, the
result is going to be the same 256 character string
'b919fbbcae38e2bdaebb6c04ed4098e5c 70563d2dc51e085f784c058ff208516'

Ò»¸öÀíÏëµÄ¹þÏ£º¯Êý°üÀ¨ÒÔÏÂÌØÕ÷£º

ËüÓ¦¸ÃºÜÈÝÒ×¼ÆËã¡£

ÄÄÅÂÖ»¸ü¸ÄÊý¾ÝÖеÄÒ»¸ö룬¹þÏ£ÖµÒ²Ó¦¸ÃÍêÈ«·¢Éú±ä»¯¡£

Ó¦¸ÃÎÞ·¨¸ù¾ÝÊä³ö¹þÏ£Öµ²Â³öÊäÈë¡£

ÄúÏÖÔÚÖªµÀ¹þÏ£º¯ÊýÊÇʲôÁ˰ɡ£ÎÒÃǽ«Ã¿¸öÇø¿éµÄ¹þÏ£Öµ¶¼´æ´¢ÔÚ Block ¶ÔÏóÄÚµÄÒ»¸ö×Ö¶ÎÖУ¬Æä×÷ÓÃÀàËÆÓÚËüËù°üº¬µÄÊý¾ÝµÄÊý×ÖÖ¸ÎÆ£º

from hashlib import sha256
import json

def compute_hash(block):
"""
A function that creates the hash of the block.
"""
block_string = json.dumps(self.__dict__, sort_keys=True)
return sha256(block_string.encode()).hexdigest()

±¸×¢£ºÔÚ´ó¶àÊý¼ÓÃÜ»õ±ÒÖУ¬ÉõÖÁ¶ÔÇø¿éÖеĸ÷¸öÊÂÎñÒ²½øÐÐÁ˹þÏ£ÔËË㣬´Ó¶øÐγÉÒ»¿Ã¹þÏ£Ê÷£¨Ò²³ÆÎª¶þ½øÖƹþÏ£Ê÷£©£¬Õâ¿ÃÊ÷µÄ¸ù¿ÉÒÔÓÃ×÷Çø¿éµÄ¹þÏ£Öµ¡£Ëü²»ÊÇÇø¿éÁ´Õý³£ÔË×÷µÄ±ØÒªÌõ¼þ£¬ËùÒÔÎÒÃǽ«Ê¡ÂÔËü£¬ÒÔ±£³Ö´úÂë¼ò½à¡£

Á´½ÓÇø¿é

ÎÒÃÇÒÑÉèÖÃÁËÇø¿é¡£Çø¿éÁ´Ó¦¸ÃÊÇÒ»¸öÇø¿é¼¯ºÏ¡£ÎÒÃÇ¿ÉÒÔ½«ËùÓÐÇø¿é¶¼´æ´¢ÔÚ Python ÁбíÖУ¨µÈЧÓÚÊý×飩¡£µ«Õ⻹²»¹»£¬ÒòΪÈç¹ûÓÐÈ˹ÊÒâÌæ»»Á˼¯ºÏÖеÄÒ»¸öÇø¿é¸ÃÔõô°ì£¿ÓÃÐ޸ĹýµÄÊÂÎñ´´½¨Ò»¸öеÄÇø¿é£¬¼ÆËã¹þÏ£Öµ£¬È»ºóÌæ»»ÈκξÉÇø¿é£¬ÕâÔÚÎÒÃǵĵ±Ç°ÊµÏÖÖв¢²»ÊÇʲôÄÑÊ£¬ÒòΪÎÒÃǻᱣ³ÖÇø¿éµÄ²»¿É¸ü¸ÄÐÔºÍ˳Ðò¡£

ÎÒÃÇÐèÒª²ÉÓÃijÖÖ;¾¶À´È·±£¶Ô¹ýÈ¥µÄÇø¿éµÄÈκθü¸Ä¶¼»áÔì³ÉÕû¸öÁ´µÄʧЧ¡£Ò»ÖÖ·½·¨ÊÇͨ¹ý¹þÏ£Öµ½«Çø¿éÁ´½ÓÆðÀ´¡£Ì¸µ½Á´½Ó£¬ÎÒÃÇÖ¸µÄÊǽ«Ç°Ò»¸öÇø¿éµÄ¹þÏ£Öµ°üº¬ÔÚµ±Ç°Çø¿éÖС£ËùÒÔ£¬Èç¹ûÈκÎÒÔǰµÄÇø¿éµÄÄÚÈÝ·¢Éú¸ü¸Ä£¬¸ÃÇø¿éµÄ¹þÏ£ÖµÒ²»á·¢Éú¸ü¸Ä£¬µ¼ÖÂÓëÏÂÒ»¸öÇø¿éÖÐµÄ previous_hash ×ֶβ»Æ¥Åä¡£

ÿ¸öÇø¿é¶¼Í¨¹ý previous_hash ×Ö¶ÎÁ´½Óµ½Ç°Ò»¸öÇø¿é£¬µ«ÊǵÚÒ»¸öÇø¿é¸ÃÈçºÎ´¦Àí£¿µÚÒ»¸öÇø¿é³ÆÎª´´Ê¼Çø¿é£¬´ó¶àÊýÇé¿öÏ£¬ËüÊÇÊÖ¶¯Éú³É»òͨ¹ýijÖÖ¶ÀÌØÂß¼­Éú³ÉµÄ¡£ÈÃÎÒÃǽ« previous_hash ×Ö¶ÎÌí¼Óµ½ Block ÀàÖУ¬²¢ÊµÏÖÎÒÃÇµÄ Blockchain ÀàµÄ³õʼ½á¹¹£¨²Î¼ûÇåµ¥ 1£©¡£

Çåµ¥ 1. ÎÒÃÇµÄ Blockchain ÀàµÄ³õʼ½á¹¹

from hashlib import sha256
import json
import time
class Block:
def__init__(self, index, transactions, timestamp, previous_hash):
self.index = index
self.transactions = transactions
self.timestamp = timestamp
self.previous_hash = previous_hash

def compute_hash(self):
block_string = json.dumps(self.__dict__, sort_keys=True)
return sha256(block_string.encode()).hexdigest()

ÕâÊÇÎÒÃÇµÄ Blockchain Àࣺ

class Blockchain:

def __init__(self):
self.unconfirmed_transactions = [] # data yet to get into blockchain
self.chain = []
self.create_genesis_block()

def create_genesis_block(self):
"""
A function to generate genesis block and appends it to
the chain.The block has index 0, previous_hash as 0, and
a valid hash.
"""
genesis_block = Block(0, [], time.time(), "0")
genesis_block.hash = genesis_block.compute_hash()
self.chain.append(genesis_block)

@property
def last_block(self):
return self.chain[-1]

ʵÏÖ¹¤×÷Á¿Ö¤Ã÷Ëã·¨

µ«ÕâÀï´æÔÚÒ»¸öÎÊÌâ¡£Èç¹ûÎÒÃǸü¸Äǰһ¸öÇø¿é£¬ÎÒÃÇ¿ÉÒԷdz£ÇáËɵØÖØÐ¼ÆËãËùÓкóÐøÇø¿éµÄ¹þÏ£Öµ£¬²¢´´½¨Ò»¸ö²»Í¬µÄÓÐÐ§Çø¿éÁ´¡£ÎªÁËÔ¤·ÀÕâÖÖÇé¿ö£¬ÎÒÃDZØÐëÈüÆËã¹þÏ£ÖµµÄÈÎÎñ±äµÃÀ§ÄѺÍËæ»ú»¯¡£

ÒÔÏÂÊÇÎÒÃÇʵÏִ˲Ù×÷µÄ·½Ê½¡£ÎÒÃDz»»á½ÓÊÜÈκÎÇø¿é¹þÏ£Öµ£¬¶øÊǶÔËüÌí¼ÓijÖÖÔ¼Êø¡£ÈÃÎÒÃÇÀ´Ìí¼ÓÒ»ÖÖÔ¼Êø£º¹þÏ£ÖµÓ¦ÒÔÁ½¸öǰµ¼Á㿪ʼ¡£ÁíÍâÎÒÃÇÖªµÀ£¬³ý·Ç¸ü¸ÄÇø¿éµÄÄÚÈÝ£¬·ñÔò¹þÏ£Öµ²»»á·¢Éú¸ü¸Ä¡£

ËùÒÔÎÒÃǽ«ÔÚÇø¿éÖÐÒýÈëÒ»¸ö³ÆÎªËæ»úÊýµÄÐÂ×ֶΡ£Ëæ»úÊý»á²»¶Ï±ä»¯£¬Ö±µ½ÎÒÃÇ»ñµÃÂú×ãÔ¼ÊøÌõ¼þµÄ¹þÏ£Öµ¡£Ç°µ¼ÁãµÄÊýÁ¿£¨ÔÚÎÒÃǵÄÀý×ÓÖÐΪֵ 2£©¾ö¶¨Á˹¤×÷Á¿Ö¤Ã÷Ëã·¨µÄ¡°ÄѶȡ±¡£Äú¿ÉÄÜ»¹×¢Òâµ½£¬ÎÒÃǵŤ×÷Á¿Ö¤Ã÷ºÜÄѼÆË㣬µ«ÔÚÎÒÃÇÈ·¶¨Ëæ»úÊýºóºÜÈÝÒ×ÑéÖ¤£¨¶ÔÓÚÑéÖ¤£¬ÄúÖ»ÐèÒªÔÙ´ÎÔËÐйþÏ£º¯Êý¼´¿É£©£º

class Blockchain:
# difficulty of PoW algorithm
difficulty = 2

"""
Previous code contd..
"""

def proof_of_work(self, block):
"""
Function that tries different values of nonce to get a hash
that satisfies our difficulty criteria.
"""
block.nonce = 0

computed_hash = block.compute_hash()
while not computed_hash.startswith('0' * Blockchain.difficulty):
block.nonce += 1
computed_hash = block.compute_hash()

return computed_hash

Çë×¢Ò⣬ûÓÐÃ÷È·µÄÂß¼­À´¿ìËÙÈ·¶¨Ëæ»úÊý£»Ö»ÄÜͨ¹ý±©Á¦ÆÆ½â¡£

½«Çø¿éÌí¼Óµ½Á´ÖÐ

Òª½«Çø¿éÌí¼Óµ½Á´ÖУ¬Ê×ÏÈÐèÒªÑéÖ¤ËùÌṩµÄ¹¤×÷Á¿Ö¤Ã÷ÊÇ·ñÕýÈ·£¬ÒÔ¼°ÒªÌí¼ÓµÄÇø¿éµÄ previous_hash ×Ö¶ÎÊÇ·ñÖ¸ÏòÁ´ÖеÄ×îÐÂÇø¿éµÄ¹þÏ£Öµ¡£

ÈÃÎÒÃÇ¿´¿´½«Çø¿éÌí¼Óµ½Á´ÖеĴúÂ룺

class Blockchain:
"""
Previous code contd..
"""
def add_block(self, block, proof):
"""
A function that adds the block to the chain after verification.
"""
previous_hash = self.last_block.hash

if previous_hash != block.previous_hash:
return False

if not self.is_valid_proof(block, proof):
return False

block.hash = proof
self.chain.append(block)
return True

def is_valid_proof(self, block, block_hash):
"""
Check if block_hash is valid hash of block and satisfies
the difficulty criteria.
"""
return (block_hash.startswith('0' * Blockchain.difficulty) and
block_hash == block.compute_hash())

ÍÚ¿ó

ÊÂÎñ×î³õ´æ´¢ÔÚÒ»¸öδȷÈÏÊÂÎñ³ØÖС£½«Î´È·ÈÏÊÂÎñ·ÅÈëÇø¿éÖв¢¼ÆË㹤×÷Á¿Ö¤Ã÷µÄ¹ý³Ì±»³ÆÎªÇø¿éÍÚ¿ó¡£Ò»µ©ÕÒµ½Âú×ãÎÒÃǵÄÔ¼ÊøÌõ¼þµÄËæ»úÊý£¬ÎÒÃǾͿÉÒÔ˵ÍÚµ½ÁËÒ»¸öÇø¿é£¬Õâ¸öÇø¿é¾Í»á·ÅÈëÇø¿éÁ´ÖС£

ÔÚ´ó¶àÊý¼ÓÃÜ»õ±Ò£¨°üÀ¨±ÈÌØ±Ò£©ÖУ¬×÷Ϊ¶ÔºÄ·ÑËãÁ¦À´¼ÆË㹤×÷Á¿Ö¤Ã÷µÄ½±Àø£¬¿ó¹¤¿ÉÒÔ»ñµÃһЩ¼ÓÃÜ»õ±Ò¡£ÒÔÏÂÊÇÎÒÃǵÄÍÚ¿óº¯ÊýµÄ¸ñʽ£º

class Blockchain:
"""
Previous code contd...
"""

def add_new_transaction(self, transaction):
self.unconfirmed_transactions.append(transaction)

def mine(self):
"""
This function serves as an interface to add the pending
transactions to the blockchain by adding them to the block
and figuring out Proof of Work.
"""
if not self.unconfirmed_transactions:
return False

last_block = self.last_block

new_block = Block(index=last_block.index + 1,
transactions=self.unconfirmed_transactions,
timestamp=time.time(),
previous_hash=last_block.hash)

proof = self.proof_of_work(new_block)
self.add_block(new_block, proof)
self.unconfirmed_transactions = []
return new_block.index

ºÃÁË£¬ÎÒÃǵŤ×÷²î²»¶àÍê³ÉÁË¡£Äú¿ÉÒÔÔÚ GitHub Éϲ鿴½ØÖÁĿǰµÄºÏ²¢´úÂë¡£

´´½¨½Ó¿Ú

ÏÖÔÚΪÎÒÃǵĽڵ㴴½¨½Ó¿Ú£¬ÒÔ±ãÓëÆäËû¶ÔµÈ½ÚµãÒÔ¼°ÎÒÃǽ«Òª¹¹½¨µÄÓ¦ÓóÌÐò½øÐн»»¥¡£ÎÒÃǽ«Ê¹Óà Flask ´´½¨Ò»¸ö REST-API À´ÓëÎÒÃÇµÄ½Úµã½øÐн»»¥¡£ÒÔÏÂÊÇËüµÄ´úÂ룺

from flask import Flask, request
import requests

app = Flask(__name__)

# the node's copy of blockchain
blockchain = Blockchain()

ÎÒÃǵÄÓ¦ÓóÌÐòÐèÒªÒ»¸ö¶ËµãÀ´Ìá½»ÐÂÊÂÎñ¡£ÎÒÃǵÄÓ¦ÓóÌÐò½«Ê¹Óô˶˵㽫ÐÂÊý¾Ý£¨Ìû×Ó£©Ìí¼Óµ½Çø¿éÁ´ÖУº

@app.route('/new_transaction', methods=['POST'])
def new_transaction():
tx_data = request.get_json()
required_fields = ["author", "content"]

for field in required_fields:
if not tx_data.get(field):
return "Invlaid transaction data", 404

tx_data["timestamp"] = time.time()

blockchain.add_new_transaction(tx_data)

return "Success", 201

ÏÂÃæÊÇ·µ»Ø½ÚµãµÄÁ´¸±±¾µÄ¶Ëµã¡£ÎÒÃǵÄÓ¦ÓóÌÐò½«Ê¹Óô˶˵ãÀ´²éѯҪÏÔʾµÄËùÓÐÌû×Ó£º

@app.route('/chain', methods=['GET'])
def get_chain():
chain_data = []
for block in blockchain.chain:
chain_data.append(block.__dict__)
return json.dumps({"length": len(chain_data),
"chain": chain_data})

ÏÂÃæÊÇÇëÇó½ÚµãÍÚ¾òδȷÈÏÊÂÎñ£¨Èç¹ûÓУ©µÄ¶Ëµã¡£ÎÒÃǽ«Ê¹Óô˶˵ã´ÓÎÒÃǵÄÓ¦ÓóÌÐò×ÔÉí·¢ÆðÒ»¸öÍÚ¿óÃüÁ

@app.route('/mine', methods=['GET'])
def mine_unconfirmed_transactions():
result = blockchain.mine()
if not result:
return "No transactions to mine"
return "Block #{} is mined.".format(result)


# endpoint to query unconfirmed transactions
@app.route('/pending_tx')
def get_pending_tx():
return json.dumps(blockchain.unconfirmed_transactions)


app.run(debug=True, port=8000)

ÏÖÔÚ£¬Äú¿ÉÒÔÌåÑéÒ»ÏÂÎÒÃǵÄÇø¿éÁ´£¬´´½¨Ò»Ð©ÊÂÎñ£¬È»ºóʹÓÃÖîÈç cURL »ò Postman Ö®ÀàµÄ¹¤¾ßÀ´ÍÚ¾òËüÃÇ¡£

½¨Á¢¹²Ê¶ºÍÈ¥ÖÐÐÄ»¯

ĿǰΪֹ£¬ÎÒÃÇʵÏֵĴúÂëÖ»ÄÜÔÚµ¥¸ö¼ÆËã»úÉÏÔËÐС£¼´Ê¹Í¨¹ý¹þÏ£ÖµÁ´½ÓÁËÇø¿é£¬ÎÒÃÇÈÔÈ»²»ÄÜÐÅÈε¥¸öʵÌå¡£ÎÒÃÇÐèÒª¶à¸ö½ÚµãÀ´Î¬»¤ÎÒÃǵÄÇø¿éÁ´¡£ ËùÒÔÈÃÎÒÃÇ´´½¨Ò»¸ö¶Ëµã£¬ÒÔ±ãÈÃÒ»¸ö½ÚµãÁ˽âÍøÂçÖÐµÄÆäËû¶ÔµÈ½Úµã£º

# the address to other participating members of the network
peers = set()

# endpoint to add new peers to the network.
@app.route('/add_nodes', methods=['POST'])
def register_new_peers():
nodes = request.get_json()
if not nodes:
return "Invalid data", 400
for node in nodes:
peers.add(node)

return "Success", 201

Äú¿ÉÄÜÒѾ­ÈÏʶµ½£¬ÔÚ¶à½Úµã·½Ãæ´æÔÚÒ»¸öÎÊÌâ¡£ÓÉÓÚ¹ÊÒâ²Ù×Ý»òÒâÍâµÄÔ­Òò£¬Ò»Ð©½ÚµãµÄÁ´¸±±¾¿ÉÄÜÓÐËù²»Í¬¡£ÔÚÕâÖÖÇé¿öÏ£¬ÎÒÃÇÐèÒªÉ̶¨²ÉÓÃÁ´µÄij¸ö°æ±¾£¬ÒÔά³ÖÕû¸öϵͳµÄÍêÕûÐÔ¡£ÎÒÃÇÐèÒª´ï³É¹²Ê¶¡£

Ò»ÖÖ¼òµ¥µÄ¹²Ê¶Ëã·¨¿ÉÄÜÊÇ£¬ÔÚÍøÂçÖеIJ»Í¬²ÎÓëÕß¹¹³ÉµÄÁ´³öÏÖ·ÖÆçʱ£¬É̶¨²ÉÓÃ×µÄÓÐЧÁ´¡£Ñ¡Ôñ´Ë·½·¨µÄÀíÓÉÊÇ£¬×µÄÁ´ÊǶÔÒÑÍê³ÉµÄ×î¶à¹¤×÷Á¿µÄÓÐЧ¹ÀË㣺

def consensus():
"""
Our simple consensus algorithm.Èç¹ûÕÒµ½Ò»¸ö¸ü³¤µÄÓÐЧÁ´£¬ÔòÓÃËüÌæ»»ÎÒÃǵÄÁ´¡£
"""
global blockchain

longest_chain = None
current_len = len(blockchain)

for node in peers:
response = requests.get('http://{}/chain'.format(node))
length = response.json()['length']
chain = response.json()['chain']
if length > current_len and blockchain.check_chain_validity(chain):
current_len = length
longest_chain = chain

if longest_chain:
blockchain = longest_chain
return True

return False

 

×îºó£¬ÎÒÃÇÐèÒª¿ª·¢Ò»ÖÖ·½·¨£¬ÈÃÈκνڵãÏòÍøÂçÐû²¼ËüÒѾ­ÍÚµ½Ò»¸öÇø¿é£¬ÒÔ±ãÿ¸öÈ˶¼ÄܸüÐÂËûÃǵÄÇø¿éÁ´£¬²¢¼ÌÐøÍÚ¾òÆäËûÊÂÎñ¡£ÆäËû½Úµã¿ÉÒÔÇáËɵØÑéÖ¤¹¤×÷Á¿Ö¤Ã÷£¬²¢½«ËüÌí¼Óµ½¸÷×ÔµÄÁ´ÖУº

# endpoint to add a block mined by someone else to the node's chain.
@app.route('/add_block', methods=['POST'])
def validate_and_add_block():
block_data = request.get_json()
block = Block(block_data["index"], block_data["transactions"],
block_data["timestamp", block_data["previous_hash"]])

proof = block_data['hash']
added = blockchain.add_block(block, proof)

if not added:
return "The block was discarded by the node", 400

return "Block added to the chain", 201

def announce_new_block(block):
for peer in peers:
url = "http://{}/add_block".format(peer)
requests.post(url, data=json.dumps(block.__dict__, sort_keys=True))

 

announce_new_block ·½·¨Ó¦ÔÚ½ÚµãÍÚµ½Ã¿¸öÇø¿éºóµ÷Óã¬ÒÔ±ã¶ÔµÈ½ÚµãÄܽ«¸ÃÇø¿éÌí¼Óµ½×Ô¼ºµÄÁ´ÖС£

¹¹½¨Ó¦ÓóÌÐò

ºÃÁË£¬ºó¶Ë¶¼ÉèÖúÃÁË¡£Äú¿ÉÒÔÔÚ GitHub Éϲ鿴µ½Ä¿Ç°ÎªÖ¹µÄ´úÂë¡£

ÏÖÔÚ£¬ÊÇʱºò´´½¨Ó¦ÓóÌÐòµÄ½Ó¿ÚÁË¡£ÎÒÃÇʹÓÃÁË Jinja2 Ä£°åÀ´³ÊÏÖÍøÒ³ºÍһЩ CSS£¬ÈÃÒ³Ãæ¿´ÆðÀ´ÃÀ¹ÛһЩ¡£

ÎÒÃǵÄÓ¦ÓóÌÐòÐèÒªÁ¬½Óµ½Çø¿éÁ´ÍøÂçÖеÄij¸ö½Úµã£¬ÒÔ±ãץȡÊý¾ÝºÍÌá½»ÐÂÊý¾Ý¡£Ò²¿ÉÄÜ´æÔÚ¶à¸ö½Úµã£º

import datetime
import json

import requests
from flask import render_template, redirect, request

from app import app

.
CONNECTED_NODE_ADDRESS = "http://127.0.0.1:8000"

posts = []

fetch_posts º¯Êý´Ó½ÚµãµÄ /chain ¶Ëµã»ñÈ¡Êý¾Ý£¬½âÎö¸ÃÊý¾Ý²¢½«ËüÃÇ´æ´¢ÔÚ±¾µØ¡£

def fetch_posts():
get_chain_address = "{}/chain".format(CONNECTED_NODE_ADDRESS)
response = requests.get(get_chain_address)
if response.status_code == 200:
content = []
chain = json.loads(response.content)
for block in chain["chain"]:
for tx in block["transactions"]:
tx["index"] = block["index"]
tx["hash"] = block["previous_hash"]
content.append(tx)

global posts
posts = sorted(content, key=lambda k: k['timestamp'],
reverse=True)

¸ÃÓ¦ÓóÌÐòÓÐÒ»¸ö HTML ±íµ¥£¬ÓÃÓÚ½ÓÊÜÓû§ÊäÈ룬ȻºóÏòÒ»¸öÒÑÁ¬½ÓµÄ½Úµã·¢³öÒ»¸ö POST ÇëÇó£¬ÒԱ㽫¸ÃÊÂÎñÌí¼Óµ½Î´È·ÈÏÊÂÎñ³ØÖС£È»ºó£¬Í¨¹ýÍøÂç¶Ô¸ÃÊÂÎñ½øÐÐÍÚ¾ò£¬×îºóÔÚÎÒÃÇË¢ÐÂÍøÕ¾ºóץȡ¸ÃÊÂÎñ£º

@app.route('/submit', methods=['POST'])
def submit_textarea():
"""
Endpoint to create a new transaction via our application.
"""
post_content = request.form["content"]
author = request.form["author"]

post_object = {
'author': author,
'content': post_content,
}

# Submit a transaction
new_tx_address = "{}/new_transaction".format(CONNECTED_NODE_ADDRESS)

requests.post(new_tx_address,
json=post_object,
headers={'Content-type': 'application/json'})

return redirect('/')

ÔËÐÐÓ¦ÓóÌÐò

´ó¹¦¸æ³É£¡¿ÉÒÔÔÚ GitHub ÉÏÕÒµ½×îÖÕ´úÂë¡£

ÒªÔËÐиÃÓ¦ÓóÌÐò£º

Æô¶¯Ò»¸öÇø¿éÁ´½Úµã·þÎñÆ÷£º

python node_server.py

ÔËÐиÃÓ¦ÓóÌÐò£º

python run_app.py

ÄúÓ¦¸ÃÄÜÔÚ http://localhost:5000 ÉÏ¿´µ½ÕýÔÚÔËÐеÄÓ¦ÓóÌÐò¡£

a.³¢ÊÔ·¢²¼Ò»Ð©Êý¾Ý£¬Äú»á¿´µ½ÀàËÆÏÂͼµÄ½á¹û£º

b.µ¥»÷ Request to mine °´Å¥£¬Äú»á¿´µ½ÀàËÆÏÂͼµÄ½á¹û£º

c.µ¥»÷ Resync °´Å¥£¬Äú»á¿´µ½Ó¦ÓóÌÐòÓëÁ´ÖØÐÂͬ²½£º

ÑéÖ¤ÊÂÎñ

Äú¿ÉÄÜ×¢Òâµ½ÁËÓ¦ÓóÌÐòÖеÄÒ»¸öȱÏÝ£ºÈκÎÈ˶¼Äܸü¸ÄÈκÎÃû³ÆºÍ·¢²¼ÈκÎÄÚÈÝ¡£½â¾ö´ËÎÊÌâµÄÒ»ÖÖ·½·¨ÊÇ£¬Ê¹Óù«Ë½ÃÜÔ¿¼ÓÃÜÀ´´´½¨ÕÊ»§¡£Ã¿¸öÐÂÓû§¶¼ÐèÒªÒ»¸ö¹«Ô¿£¨ÀàËÆÓÚÓû§Ãû£©ºÍ˽Կ£¬²ÅÄÜÔÚÎÒÃǵÄÓ¦ÓóÌÐòÖз¢²¼ÄÚÈÝ¡£ÕâЩÃÜÔ¿¿ÉÒԳ䵱Êý×ÖÇ©Ãû¡£¹«Ô¿Ö»ÄܶÔʹÓÃÏàӦ˽Կ¼ÓÃܵÄÄÚÈݽøÐнâÃÜ¡£ÔÚ½«ÊÂÎñÌí¼Óµ½ÈκÎÇø¿é֮ǰ£¬»áʹÓÃ×÷ÕߵĹ«Ô¿¶ÔÆä½øÐÐÑéÖ¤¡£ÕâÑù£¬ÎÒÃǾÍÖªµÀÊÇ˭дµÄÕâÌõÏûÏ¢¡£

½áÊøÓï

±¾½Ì³Ì½éÉÜÁ˹«ÓÐÇø¿éÁ´µÄ»ù´¡ÖªÊ¶¡£Èç¹ûÄúÒ»Ö±ÔÚ¸úËæ²Ù×÷£¬ÄÇôÄúÒѾ­´ÓÁ㿪ʼʵÏÖÁËÒ»¸öÇø¿éÁ´£¬²¢¹¹½¨ÁËÒ»¸ö¼òµ¥Ó¦ÓóÌÐòÀ´ÔÊÐíÓû§ÔÚ¸ÃÇø¿éÁ´ÉϹ²ÏíÐÅÏ¢¡£

   
2478 ´Îä¯ÀÀ       31
Ïà¹ØÎÄÕÂ

ÊÖ»úÈí¼þ²âÊÔÓÃÀýÉè¼ÆÊµ¼ù
ÊÖ»ú¿Í»§¶ËUI²âÊÔ·ÖÎö
iPhoneÏûÏ¢ÍÆËÍ»úÖÆÊµÏÖÓë̽ÌÖ
AndroidÊÖ»ú¿ª·¢£¨Ò»£©
Ïà¹ØÎĵµ

Android_UI¹Ù·½Éè¼Æ½Ì³Ì
ÊÖ»ú¿ª·¢Æ½Ì¨½éÉÜ
androidÅÄÕÕ¼°ÉÏ´«¹¦ÄÜ
Android½²ÒåÖÇÄÜÊÖ»ú¿ª·¢
Ïà¹Ø¿Î³Ì

Android¸ß¼¶Òƶ¯Ó¦ÓóÌÐò
Androidϵͳ¿ª·¢
AndroidÓ¦Óÿª·¢
ÊÖ»úÈí¼þ²âÊÔ