def create_token( self, asset: Asset, required_confirmation_count: int = 1) -> "CryptoTokenCreation": """Create a token on behalf of this user.""" assert asset.id assert asset.supply assert asset.network.id ensure_positive(asset.supply) dbsession = Session.object_session(self) crypto_account = self.get_or_create_account(asset) # One transaction can contain multiple assets to the same address. Each recognized asset should result to its own operation. existing = dbsession.query(CryptoTokenCreation).join( CryptoAddressAccount).join(Account).join(Asset).filter( Asset.id == asset.id).one_or_none() if existing: raise ValueError("Token for this asset already created.") # Create the operation op = CryptoTokenCreation(network=asset.network) op.crypto_account = crypto_account op.holding_account = Account(asset=asset) dbsession.flush() op.holding_account.do_withdraw_or_deposit(asset.supply, "Initial supply") op.required_confirmation_count = required_confirmation_count return op
def withdraw(self, amount: Decimal, to_address: bytes, note: str, required_confirmation_count=1) -> "CryptoAddressWithdraw": """Initiates the withdraw operation. :to_address: External address in binary format where we withdraw """ assert to_address assert self.id assert self.account assert self.account.id assert isinstance(amount, Decimal) assert isinstance(note, str) ensure_positive(amount) self.account.asset.ensure_not_frozen() network = self.account.asset.network assert network.id op = CryptoAddressWithdraw(network=network) op.crypto_account = self op.holding_account = Account(asset=self.account.asset) op.external_address = to_address op.required_confirmation_count = required_confirmation_count dbsession = Session.object_session(self) dbsession.add(op) dbsession.flush() # Give ids # Lock assetes in transfer to this object Account.transfer(amount, self.account, op.holding_account, note) return op
def create_token(self, asset: Asset, required_confirmation_count:int=1) -> "CryptoTokenCreation": """Create a token on behalf of this user.""" assert asset.id assert asset.supply assert asset.network.id ensure_positive(asset.supply) dbsession = Session.object_session(self) crypto_account = self.get_or_create_account(asset) # One transaction can contain multiple assets to the same address. Each recognized asset should result to its own operation. existing = dbsession.query(CryptoTokenCreation).join(CryptoAddressAccount).join(Account).join(Asset).filter(Asset.id==asset.id).one_or_none() if existing: raise ValueError("Token for this asset already created.") # Create the operation op = CryptoTokenCreation(network=asset.network) op.crypto_account = crypto_account op.holding_account = Account(asset=asset) dbsession.flush() op.holding_account.do_withdraw_or_deposit(asset.supply, "Initial supply") op.required_confirmation_count = required_confirmation_count return op
def deposit(self, amount: Decimal, asset: Asset, txid: bytes, note: str) -> "CryptoAddressDeposit": """External transaction incoming to this address. If called twice with the same txid, returns the existing operation, so that we don't process the deposit twice. The actual account is credited when this operation is resolved. """ # Check validity of this object assert self.id assert asset assert asset.id assert self.address assert isinstance(asset, Asset) assert type(txid) == bytes ensure_positive(amount) dbsession = Session.object_session(self) crypto_account = self.get_or_create_account(asset) # TODO: Use opid instead of txid here # One transaction can contain multiple assets to the same address. Each recognized asset should result to its own operation. existing = dbsession.query(CryptoAddressDeposit).filter_by( txid=txid).join(Account).filter_by( asset_id=asset.id).one_or_none() if existing: return existing # Create the operation op = CryptoAddressDeposit(network=asset.network) op.crypto_account = crypto_account op.holding_account = Account(asset=asset) op.txid = txid dbsession.flush() op.holding_account.do_withdraw_or_deposit(amount, note) return op
def withdraw(self, amount: Decimal, to_address: bytes, note: str, required_confirmation_count=1) -> "CryptoAddressWithdraw": """Initiates the withdraw operation. :to_address: External address in binary format where we withdraw """ assert to_address assert isinstance(to_address, bytes) assert self.id assert self.account assert self.account.id assert isinstance(amount, Decimal) assert isinstance(note, str) ensure_positive(amount) self.account.asset.ensure_not_frozen() network = self.account.asset.network assert network.id op = CryptoAddressWithdraw(network=network) op.crypto_account = self op.holding_account = Account(asset=self.account.asset) op.external_address = to_address op.required_confirmation_count = required_confirmation_count dbsession = Session.object_session(self) dbsession.add(op) dbsession.flush() # Give ids # Lock assetes in transfer to this object Account.transfer(amount, self.account, op.holding_account, note) return op
def deposit(self, amount: Decimal, asset: Asset, txid: bytes, note: str) -> "CryptoAddressDeposit": """External transaction incoming to this address. If called twice with the same txid, returns the existing operation, so that we don't process the deposit twice. The actual account is credited when this operation is resolved. """ # Check validity of this object assert self.id assert asset assert asset.id assert self.address assert isinstance(asset, Asset) assert type(txid) == bytes ensure_positive(amount) dbsession = Session.object_session(self) crypto_account = self.get_or_create_account(asset) # TODO: Use opid instead of txid here # One transaction can contain multiple assets to the same address. Each recognized asset should result to its own operation. existing = dbsession.query(CryptoAddressDeposit).filter_by(txid=txid).join(Account).filter_by(asset_id=asset.id).one_or_none() if existing: return existing # Create the operation op = CryptoAddressDeposit(network=asset.network) op.crypto_account = crypto_account op.holding_account = Account(asset=asset) op.txid = txid dbsession.flush() op.holding_account.do_withdraw_or_deposit(amount, note) return op