lto / api
LTO Network 客户端
Requires
- php: >=7.2.0
- ext-json: *
- ext-sodium: *
- legalthings/base58-compat: ^0.1.0
- psr/http-message: ^1.0
- psr/http-server-middleware: ^1.0
Requires (Dev)
- ext-curl: *
- guzzlehttp/guzzle: ^7.2
- jasny/php-code-quality: ^2.6
Conflicts
- dev-master
- v0.3.0
- v0.2.7
- v0.2.6
- v0.2.5
- v0.2.4
- v0.2.3
- v0.2.2
- v0.2.1
- v0.2.0
- v0.1.12
- v0.1.11
- v0.1.10
- v0.1.9
- v0.1.8
- v0.1.7
- v0.1.6
- v0.1.5
- v0.1.4
- v0.1.3
- v0.1.2
- v0.1.1
- v0.1.0
- dev-multicurve
- dev-no-curl
- dev-txv3
- dev-transactions-v3
- dev-mainnet-txs
- dev-seed-nonce
- dev-remove-random-nonce-php5
- dev-php7
- dev-remove-random-nonce
- dev-fix-signature
- dev-sign-pass-string
- dev-sign-tests
- dev-remove-port
This package is auto-updated.
Last update: 2024-09-19 17:54:10 UTC
README
PHP 的 LTO Network 客户端
签名和地址对于(私有)事件链和公共链都适用。
安装
composer require lto/api
账户
创建
从种子创建账户
$seedText = "manage manual recall harvest series desert melt police rose hollow moral pledge kitten position add"; $factory = new LTO\AccountFactory('T'); // 'T' for testnet, 'L' for mainnet $account = $factory->seed($seedText);
从签名密钥创建账户
$secretKey = 'wJ4WH8dD88fSkNdFQRjaAhjFUZzZhV5yiDLDwNUnp6bYwRXrvWV8MJhQ9HL9uqMDG1n7XpTGZx7PafqaayQV8Rp'; $factory = new LTO\AccountFactory('T'); // 'T' for testnet, 'L' for mainnet $account = $factory->create($secretKey);
从完整信息创建账户
$accountInfo = [ 'address' => '3PLSsSDUn3kZdGe8qWEDak9y8oAjLVecXV1', 'sign' => [ 'secretkey' => 'wJ4WH8dD88fSkNdFQRjaAhjFUZzZhV5yiDLDwNUnp6bYwRXrvWV8MJhQ9HL9uqMDG1n7XpTGZx7PafqaayQV8Rp', 'publickey' => 'FkU1XyfrCftc4pQKXCrrDyRLSnifX1SMvmx1CYiiyB3Y' ], 'encrypt' => [ 'secretkey' => 'BnjFJJarge15FiqcxrB7Mzt68nseBXXR4LQ54qFBsWJN', 'publickey' => 'BVv1ZuE3gKFa6krwWJQwEmrLYUESuUabNCXgYTmCoBt6' ] ]; $factory = new LTO\AccountFactory('T'); // 'T' for testnet, 'L' for mainnet $account = $factory->create($accountInfo);
指定的属性将进行验证。省略的属性将在可能的情况下生成。
签名(ED25519)
签名消息
$signature = $account->sign('hello world'); // Base58 encoded signature
验证签名
if (!$account->verify($signature, 'hello world')) { throw new RuntimeException('invalid signature'); }
加密(X25519)
为另一个账户加密消息
$message = 'hello world'; $recipientPublicKey = "HBqhfdFASRQ5eBBpu2y6c6KKi1az6bMx8v1JxX4iW1Q8"; // base58 encoded X25519 public key $recipient = $factory->createPublic(null, $recipientPublicKey); $cyphertext = $account->encryptFor($recipient, $message); // Raw binary, not encoded
您可以使用 $account->encryptFor($account, $message);
为自己加密消息。
解密来自另一个账户的消息
$senderPublicKey = "HBqhfdFASRQ5eBBpu2y6c6KKi1az6bMx8v1JxX4iW1Q8"; // base58 encoded X25519 public key $sender = $factory->createPublic(null, $senderPublicKey); $message = $account->decryptFrom($sender, $cyphertext);
您可以使用 $account->decryptFrom($account, $message);
解密来自自己的消息。
公共层
use LTO\Transaction\Transfer; use LTO\PublicNode; $node = new PublicNode('https://nodes.lto.network'); $amount = 1000.0; // Amount of LTO to transfer $recipient = "3Jo1JCrBvnWCg37VDxMXAjYhsS9rRDLBSze"; $transferTx = (new Transfer($amount, $recipient)) ->signWith($account) ->broadcastTo($node);
私有层
事件链
创建新的事件链
$chain = $account->createEventChain(); // Creates an empty event chain with a valid id and last hash
注意:您需要添加一个身份作为链上的第一个事件。这不是自动完成的。
创建并签名事件并将其添加到现有事件链
$body = [ '$schema' => "http://specs.example.com/message#", 'content' => "Hello world!" ]; $chainId = "JEKNVnkbo3jqSHT8tfiAKK4tQTFK7jbx8t18wEEnygya"; $chainLastHash = "3yMApqCuCjXDWPrbjfR5mjCPTHqFG8Pux1TxQrEM35jj"; $chain = new LTO\EventChain($chainId, $chainLastHash); $chain->add(new Event($body))->signWith($account);
您需要链 ID 和最后一个事件的哈希来使用现有链。
HTTP 身份验证
签名 HTTP 消息的描述在 IETF 草案 draft-cavage-http-signatures-10 中。
可以使用 HTTP Authentication library 来签名和验证 PSR-7 请求。
此库可以与 HTTP 身份验证库一起使用。`keyId` 应该是 base58 编码的公钥。
对于 `POST` 和 `PUT` 请求,建议创建 HTTP Digest(《RFC 3230`)。这是一个体哈希,间接地将体包含在签名中。请参阅《HTTP Digest library`>。
创建 HTTP 身份验证服务
use Jasny\HttpSignature\HttpSignature; $secretKey = 'wJ4WH8dD88fSkNdFQRjaAhjFUZzZhV5yiDLDwNUnp6bYwRXrvWV8MJhQ9HL9uqMDG1n7XpTGZx7PafqaayQV8Rp'; $factory = new LTO\AccountFactory('T'); // 'T' for testnet, 'L' for mainnet $ourAccount = $factory->create($secretKey); $service = new HttpSignature( ['ed25519', 'ed25519-sha256'], new SignCallback($ourAccount), new VerifyCallback($accountFactory) );
服务器中间件
创建服务器中间件以验证传入请求。
可以使用 LTO\Account\ServerMiddleware
为包含 `signature_key_id` 属性的服务器请求设置 account
属性。
use Jasny\HttpDigest\HttpDigest; use Jasny\HttpDigest\ServerMiddleware as DigestMiddleware; use Jasny\HttpDigest\Negitiation\DigestNegotiator; use Jasny\HttpSignature\HttpSignature; use Jasny\HttpSignature\ServerMiddleware as SignatureMiddleware; use LTO\Account\ServerMiddleware as AccountMiddleware; use Relay\RelayBuilder; $factory = new LTO\AccountFactory('T'); // 'T' for testnet, 'L' for mainnet $ourAccount = $factory->create($secretKey); $digestService = HttpDigest(new DigestNegotiator(), ["SHA-256"]); $signatureService = new HttpSignature( ['ed25519', 'ed25519-sha256'], function() { throw new \LogicException('sign not supported'); }, new VerifyCallback($accountFactory) ); $relayBuilder = new RelayBuilder($resolver); $relay = $relayBuilder->newInstance([ (new DigestMiddleware($digestService))->asDoublePass(), (new SignatureMiddleware($signatureService))->asDoublePass(), (new AccountMiddleware($factory))->asDoublePass(), ]);
服务器中间件实现了 PSR-15 MiddlewareInterface
以支持单次传递,并返回双次传递的回调,通过 asDoublePass()
方法。
客户端中间件
创建客户端中间件以签名传出请求。
use GuzzleHttp\HandlerStack; use GuzzleHttp\Client; use Jasny\HttpDigest\HttpDigest; use Jasny\HttpDigest\ClientMiddleware as DigestMiddleware; use Jasny\HttpDigest\Negitiation\DigestNegotiator; use Jasny\HttpSignature\HttpSignature; use Jasny\HttpSignature\ClientMiddleware as SignatureMiddleware; $secretKey = 'wJ4WH8dD88fSkNdFQRjaAhjFUZzZhV5yiDLDwNUnp6bYwRXrvWV8MJhQ9HL9uqMDG1n7XpTGZx7PafqaayQV8Rp'; $factory = new LTO\AccountFactory('T'); // 'T' for testnet, 'L' for mainnet $ourAccount = $factory->create($secretKey); $digestService = HttpDigest(new DigestNegotiator(), ["SHA-256"]); $signatureService = new HttpSignature( ['ed25519', 'ed25519-sha256'], new SignCallback($ourAccount), function() { throw new \LogicException('verify not supported'); } ); $signatureMiddleware = new SignatureMiddleware( $service->withAlgorithm('ed25519-sha256'), $ourAccount->getPublicKey() ); $stack = new HandlerStack(); $stack->push((new DigestMiddleware($digestService))->forGuzzle()); $stack->push($signatureMiddleware->forGuzzle()); $client = new Client(['handler' => $stack]);
命令行脚本
从种子生成账户
从 stdin
获取种子以生成账户信息。
$ vendor/bin/lto-seed <<< "manage manual recall harvest series desert melt police rose hollow moral pledge kitten position add"
address: 3JmCa4jLVv7Yn2XkCnBUGsa7WNFVEMxAfWe
sign:
secretkey: 4zsR9xoFpxfnNwLcY4hdRUarwf5xWtLj6FpKGDFBgscPxecPj2qgRNx4kJsFCpe9YDxBRNoeBWTh2SDAdwTySomS
publickey: GjSacB6a5DFNEHjDSmn724QsrRStKYzkahPH67wyrhAY
encrypt:
secretkey: 4q7HKMbwbLcG58iFV3pz4vkRnPTwbrY9Q5JrwnwLEZCC
publickey: 6fDod1xcVj4Zezwyy3tdPGHkuDyMq8bDHQouyp5BjXsX
默认情况下生成主网(L
)地址。通过将 T
作为参数传递来创建测试网地址。
$ vendor/bin/lto-seed T <<< "manage manual recall harvest series desert melt police rose hollow moral pledge kitten position add"
账户信息
从密钥(密钥)显示账户信息。密钥应该是 base58 编码的。
$ vendor/bin/lto-account 4zsR9xoFpxfnNwLcY4hdRUarwf5xWtLj6FpKGDFBgscPxecPj2qgRNx4kJsFCpe9YDxBRNoeBWTh2SDAdwTySomS
address: 3JmCa4jLVv7Yn2XkCnBUGsa7WNFVEMxAfWe
sign:
secretkey: 4zsR9xoFpxfnNwLcY4hdRUarwf5xWtLj6FpKGDFBgscPxecPj2qgRNx4kJsFCpe9YDxBRNoeBWTh2SDAdwTySomS
publickey: GjSacB6a5DFNEHjDSmn724QsrRStKYzkahPH67wyrhAY
encrypt:
secretkey: 4q7HKMbwbLcG58iFV3pz4vkRnPTwbrY9Q5JrwnwLEZCC
publickey: 6fDod1xcVj4Zezwyy3tdPGHkuDyMq8bDHQouyp5BjXsX
默认情况下生成主网(L
)地址。通过将 T
作为第三个参数传递来创建测试网地址。
$ vendor/bin/lto-seed 4zsR9xoFpxfnNwLcY4hdRUarwf5xWtLj6FpKGDFBgscPxecPj2qgRNx4kJsFCpe9YDxBRNoeBWTh2SDAdwTySomS T
签名消息
签名消息(从 stdin
)。密钥应该是 base58 编码的。输出签名和哈希(base58 编码)。
$ cat message.json | vendor/bin/lto-sign 4zsR9xoFpxfnNwLcY4hdRUarwf5xWtLj6FpKGDFBgscPxecPj2qgRNx4kJsFCpe9YDxBRNoeBWTh2SDAdwTySomS
signature: 5i9gBaHwg9UFPuwU63LBdBR29yZdRDstWM9z7oo8GzevWhBdAAWwCSRUQbPLaCT3nFgjbQuuWxVQckzCd3CoFig4
hash: 42TEXg1vFAbcJ65y7qdYG9iCPvYfy3NDdVLd75akX2P5