Este artigo non trata sobre as criptomoedas nin as finanzas descentralizadas. En cambio, exploraremos as cadeas de bloques EVM públicas e como se poden usar no teu próximo proxecto, dependendo das túas necesidades e obxectivos específicos. Mergullarei nos pros, contras e exemplos prácticos, usando a biblioteca 0xweb na que estiven traballando.
Xa está en marcha. Só ten que definir o seu modelo de datos como un contrato e implantalo.
Unha vez que se carguen os seus datos, permanecerán accesibles mentres funcione a cadea de bloques. Podo asumir que será moito máis longo que a outra subscrición de hospedaxe.
A separación dos procesos de lectura e escritura na cadea de bloques garante o 100% de tempo de actividade para as operacións de lectura, especialmente cando se aproveitan varios provedores de RPC para a redundancia.
As cadeas de bloques proporcionan inherentemente un maior nivel de seguridade que as solucións de hospedaxe convencionais. Os exploits de datos só son posibles se existen vulnerabilidades na lóxica do modelo de datos.
A menos que estean cifrados, os teus datos permanecerán abertos, accesibles e verificables por calquera persoa, promovendo a transparencia.
Os nomes de dominio non son necesarios para este tipo de backend. Pola contra, pódese utilizar unha lista de provedores de nodos descentralizados, o que permite ás bibliotecas clientes seleccionar a opción máis eficiente para os usuarios finais.
Grazas ás funcións anteriores, os backends baseados en blockchain xeran inherentemente a confianza dos usuarios ao garantir a seguridade dos datos e a dispoñibilidade 24 horas ao día, 7 días ao día, aínda que se deteñan o mantemento e o desenvolvemento do proxecto.
Podes integrar outros modelos de datos almacenados na cadea de bloques ou outros proxectos poden construír a partir do teu modelo de datos.
Os usuarios poden aproveitar numerosos proxectos de terceiros para supervisar ou automatizar accións, ampliando significativamente as posibilidades do seu modelo de datos.
Pódese acceder aos datos desde calquera punto do pasado.
Cargue eventos personalizados históricos ou use WebSockets para escoitar eventos entrantes en tempo real, permitindo respostas dinámicas das aplicacións.
O concepto de "cartera" permite aos usuarios autenticarse asinando mensaxes, proporcionando unha identificación do usuario sen problemas e descentralizada.
Os usuarios poden modificar ou ampliar os datos do seu almacenamento en función dos permisos que defina. É importante destacar que os custos destas modificacións corren a cargo dos propios usuarios. Ao seleccionar unha cadea de bloques de baixo custo, estas taxas poden permanecer insignificantes, a miúdo ascendendo a uns poucos céntimos por transacción.
Aínda que segue un verdadeiro modelo de pago por uso, só pagas polos SLOT nos que almacenas. Cada SLOT ten 32 bytes, custa 20000 GAS escribir novos datos ou 5000 GAS actualizar os datos. Tomemos Polygon como exemplo, cun prezo de GAS de 30 gwei e un prezo de 0,60 $ POL.
20000 GAS × 30 gwei = 0,008 POL × 0,60 $ = 0,00032 $
Isto é moito, polo que o emoji "Disquete" representa as cantidades de almacenamento da mellor maneira, o que significa que é o máis adecuado para conxuntos de datos máis pequenos se pagas pola túa conta. Non obstante, unha vantaxe única é que os usuarios poden asumir os custos do seu propio almacenamento e accións, unha característica que non se atopa noutras tecnoloxías. Aínda que este enfoque pode dificultar a adopción masiva da túa aplicación, é amplamente aceptado na comunidade blockchain.
Os modelos de datos Blockchain admiten funcións para interactuar cos datos, pero as súas capacidades computacionais teñen limitacións. Estas limitacións dependen dos nodos RPC que use para as accións de lectura e dos estritos límites de GAS impostos ás accións de escritura (transaccións). Aínda que as operacións básicas, os bucles e as pilas de chamadas máis profundas adoitan ser manexables, a cadea de bloques non é adecuada para cargas de traballo computacionais pesadas.
Dito isto, dados os tamaños de datos relativamente pequenos normalmente implicados, os límites existentes adoitan ser suficientes para a maioría dos casos de uso.
Se es novo no desenvolvemento da cadea de bloques, quizais escoitases que é complicado e difícil comezar. Non obstante, isto non é certo. O desenvolvemento da cadea de bloques utiliza conceptos, semántica e sintaxe familiares, o que facilita a aprendizaxe do que parece.
https://github.com/0xweb-org/examples-backend
Para este artigo, creemos un contrato de xestor de versións da aplicación. Imaxina que tes unha aplicación de escritorio que require un backend para comprobar as novas versións e recuperar a ligazón de descarga sempre que se publique unha nova versión. A continuación móstrase o contrato final, que demostra a maioría dos conceptos clave:
import { Ownable } from "@openzeppelin/contracts/access/Ownable.sol"; struct Package { uint version; uint timestamp; string url; bytes32 sha256; } contract AppVersionManager is Ownable { // Events that are emitted on data updates event NewApplicationInfo(); event NewPackage(uint version, uint timestamp); // Custom error, when title for the application is empty error TitleIsEmpty(); // Some application information string public title; // @TODO: add further application related properties if required // Latest package Package public package; // Track all versions and their packages mapping (uint => Package) public packages; // List of all previous versions uint[] public versions; constructor () Ownable(msg.sender) { } function updateInfo(string calldata newTitle) external onlyOwner { if (bytes(newTitle).length == 0) { revert TitleIsEmpty(); } title = newTitle; emit NewApplicationInfo(); } function updatePackage(Package calldata newPackage) external onlyOwner { require(newPackage.version > package.version, "Newer package already published"); packages[package.version] = package; package = newPackage; versions.push(package.version); emit NewPackage(package.version, block.timestamp); } function findPackageAtTimestamp (uint timestamp) external view returns (Package memory) { if (package.timestamp <= timestamp) { return package; } // the countdown loop to find the latest package for the timestamp int i = int(versions.length); while (--i > -1) { Package memory pkg = packages[versions[uint(i)]]; if (pkg.timestamp <= timestamp) { return pkg; } } revert("No package found"); } function getPackage (uint version) external view returns (Package memory) { if (version == package.version) { return package; } return packages[version]; } }
Todos os desenvolvedores poden ler e comprender este código cun mínimo esforzo. Se estás familiarizado con TypeScript, a maioría dos conceptos aquí xa terán sentido. Para que quede aínda máis claro, creei un exemplo de TypeScript equivalente: AppVersionManager.ts 🔗 .
En termos sinxelos, un contrato en Solidity pódese considerar unha instancia de clase con estado . Os conceptos de propiedades, métodos, tipos e herdanza xa son ben coñecidos na programación orientada a obxectos. O concepto principal a explicar aquí é o modificador onlyOwner
(similar a un decorador en TypeScript).
Cada conta de blockchain é esencialmente un par de chaves privadas e públicas. O ID da conta, coñecido como enderezo , deriva da chave pública. Cando se executa unha transacción, o enderezo do remitente pásase como msg.sender
. Usando isto, podemos almacenar o teu enderezo no construtor (durante a implantación do contrato). Máis tarde, o modificador onlyOwner
garante que só ti, como propietario do contrato, podes executar as funcións updateInfo
e updatePackage
. Se outra persoa intenta estas accións, a transacción reverterase. O modificador onlyOwner
é proporcionado polo contrato Ownable
, que forma parte da ampla biblioteca OpenZeppelin . Esta biblioteca inclúe moitos outros contratos útiles para axilizar o desenvolvemento da cadea de bloques.
Outro tema importante a tratar é o concepto de Proxies , que divide o almacenamento e a implementación en dous contratos separados. As implementacións de contratos en Solidity son inmutables, o que significa que non podes engadir novas funcións ou propiedades despois da implantación. Para evitar isto, pode implementar un contrato de "proxy". O proxy xestiona o almacenamento e só contén unha función fallback
, que delega as chamadas ao contrato de implementación mantendo o contexto de almacenamento do proxy.
Este concepto pode parecer complexo, pero é semellante a this
funciona en JavaScript. Aquí tes unha analoxía rápida para axudar a aclarar:
const foo = new Proxy({ bar: 'Lorem' }, { get (obj, prop) { return fooImplementation[prop].bind(obj) }, }); const fooImplementation = { logValue () { console.log('Bar value:', this.bar) } } foo.logValue();
O contrato de representación ten unha referencia ao contrato de execución. Se queres engadir novas funcións, só tes que implementar un novo contrato de implementación e actualizar o proxy para facer referencia a este novo contrato, reenviando as chamadas de función á instancia actualizada. É un proceso sinxelo, pero hai un caso extremo a considerar: os construtores.
Ao implementar un contrato de implementación, o seu construtor opera dentro do almacenamento do propio contrato de implementación. Isto significa que setters como title = "Hello World"
non modificarán o almacenamento do proxy. Para solucionar isto, usamos o concepto de función inicializadora :
initialize
.initialize
no contexto do contrato de proxy.
Como resultado, ao actualizar a propiedade title
, por exemplo, actualizarase correctamente no almacenamento do proxy.
Aquí tes unha versión de implementación actualizada do noso AppVersionManager: AppVersionManagerUpgradeable.sol .
O contrato de proxy en si é bastante universal e independente da implementación. Na biblioteca OpenZeppelin están dispoñibles varios estándares coñecidos para proxies.
Co coñecemento destes conceptos e os exemplos anteriores, estás preparado para desenvolver contratos intelixentes para os teus casos comerciais.
En primeiro lugar, temos que seleccionar a cadea de bloques onde queremos implantar o noso contrato. Para este exemplo, escollín Polygon. Ofrece baixos custos de transacción, existe desde hai moito tempo e ten un bo desempeño constantemente. A súa infraestrutura estable e eficiente, combinada cun valor total bloqueado (TVL) de 0.900 millóns de dólares, fai que sexa unha opción fiable. Implementar os teus contratos nas cadeas de bloques públicas significa convivir con entidades financeiras. A métrica TVL reflicte a confianza que estas institucións depositan na fiabilidade da cadea de bloques.
Ademais, se as condicións cambian, sempre podes redistribuír o contrato a outra cadea de bloques no futuro.
O proxecto de demostración tamén serve como repositorio de proba de CI, polo que todos os comandos pódense atopar aquí: https://github.com/0xweb-org/examples-backend/blob/master/deploy-cli.sh
# Install 0xweb library from NPM into the prject folder npm i 0xweb # Install required dependencies to compile/deploy *.sol files npx 0xweb init --hardhat --openzeppelin # Create or import the account. Private key will be encrypted with pin AND machine key. npx 0xweb accounts new --name foo --pin test --login # Save the private key securly and ensure the account has some POL tokens # Deploy. The foo account is selected as default. npx 0xweb deploy ./contracts/AppVersionManager.sol --chain polygon --pin test # Set title npx 0xweb c write AppVersionManager updateInfo --newTitle MySuperApp --pin test # Set latest package information npx 0xweb c write AppVersionManager updatePackage --arg0 'load(./data/package.json)' --pin test
Con só algúns comandos, implementou o contrato e actualizou os datos. Iso é todo para o backend: agora está funcionando "para sempre" sen necesidade de máis accións do teu lado. Os custos desta implantación, a un prezo de GAS de 70 gwei e un prezo de POL de 0,51 dólares, serían:
| GAS | POL | $ |
---|---|---|---|
Implantar | 850352 | 0,059 | 0,03 |
Gardar título | 47517 | 0,0033 | 0,001 |
Gardar datos do paquete | 169549 | 0,0118 | 0,006 |
Total | | | 0,037 |
Gastas só 4 céntimos para configurar un servizo descentralizado , seguro e de longa duración sen necesidade de mantemento .
Para consultar os datos do teu contrato, necesitarás provedores de nodos RPC. Decenas de provedores gratuítos están dispoñibles en https://chainlist.org . Podes escoller varios provedores, e unha boa biblioteca Web3 pode utilizar unha estratexia de round-robin no tempo de execución para seleccionar a máis eficiente para os teus usuarios finais. Con 0xweb, as clases de TypeScript ou JavaScript xeradas non só seleccionan os mellores puntos finais, senón que tamén abstraen toda a comunicación blockchain. Os clientes conteñen métodos de alto nivel para obter datos, facendo que o proceso sexa fluido e eficiente.
# The deploy command also generates the class, but manual install is also possible npx 0xweb i 0x<address> --name AppVersionManager --chain polygon
import { AppVersionManager } from './0xc/polygon/AppVersionManager/AppVersionManager' const manager = new AppVersionManager(); console.log(`Title`, await manager.title()); console.log(`Package`, await manager.package());
Para outras linguaxes de programación, hai numerosas bibliotecas dispoñibles para simplificar a consulta da cadea de bloques. Despois da implantación, terás o enderezo do contrato e ABI (interface).
Alternativamente, pode iniciar un servidor de middleware para consultar os datos do contrato mediante 0xweb.
npx 0xweb server start --port 3000 curl http://localhost:3000/api/c/read/AppVersionManager/package?chain=polygon
Unha vantaxe é que non precisa incluír ningunha biblioteca na súa aplicación: solicitudes HTTP sen procesar. Non obstante, este enfoque depende dun servidor adicional que terás que xestionar. Moitas veces é mellor consultar a cadea de bloques directamente usando clases xeradas por 0xweb ou outras bibliotecas de cadea de bloques dispoñibles.
Este artigo mostrou como as cadeas de bloques poden ser sinxelas e poderosas, ofrecendo vantaxes únicas en comparación coas solucións de hospedaxe tradicionais.
No seguinte artigo, penso explorar redes de almacenamento BLOB descentralizadas como Greenfield e Arweave, destacando as súas características e vantaxes.
Se tes algunha suxestión ou idea sobre funcións adicionais para incluír na biblioteca 0xweb, non dubides en compartilas nos comentarios ou en contacto directamente en [email protected] .