Skip to content

Commit

Permalink
Feat/java sdk (#538)
Browse files Browse the repository at this point in the history
* feat: add doc store

* feat: add java sdk

* feat: add java test

* fix: update pom group id

* feat: add add doc

* feat: add add doc

* fix: update readme

* feat: add doc query

* fix: remove the main

* feat: add usage

* feat: remove the english

* feat: add Readme
  • Loading branch information
imotai authored Jul 3, 2023
1 parent 092e2ed commit 5359790
Show file tree
Hide file tree
Showing 19 changed files with 764 additions and 11 deletions.
3 changes: 3 additions & 0 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -69,6 +69,9 @@ jobs:
ROOT_DIR=`pwd`
cd $ROOT_DIR/sdk && yarn && make
cd $ROOT_DIR/sdk && yarn test --coverage
- name: Rust java sdk test
run: |
cd java && mvn test
- uses: codecov/codecov-action@v3
with:
token: ${{secrets.COV_TOKEN}}
Expand Down
14 changes: 5 additions & 9 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -10,8 +10,9 @@
![GitHub release (latest by date)](https://img.shields.io/github/v/release/dbpunk-labs/db3?color=green&display_name=tag&label=db3&logo=db3&logoColor=https%3A%2F%2Favatars.githubusercontent.com%2Fu%2F102341693%3Fs%3D96%26v%3D4&style=flat-square)[![Twitter Follow](https://img.shields.io/twitter/follow/Db3Network?style=flat-square)](https://twitter.com/Db3Network)
[![GitPOAP Badge](https://public-api.gitpoap.io/v1/repo/dbpunk-labs/db3/badge)](https://www.gitpoap.io/gh/dbpunk-labs/db3)
[![Discord](https://badgen.net/badge/icon/discord?icon=discord&label)](https://discord.gg/sz3bmZx2uh)
![Java SDK](https://img.shields.io/maven-central/v/network.db3/sdk)
![npm](https://img.shields.io/npm/dw/db3.js?style=flat-square)

**English**

# DB3 Network

Expand Down Expand Up @@ -83,7 +84,7 @@ if you have any questions, please feel free to ask us for help and you can find

# Try Our Cloud Sandbox

* [Console](https://console.cloud.db3.network/console/home)
* [Console](https://console.cloud.db3.network/console/home):https://console.cloud.db3.network/console/home
* Data Rollup Node: https://rollup.cloud.db3.network
* Data Index Node: https://index.cloud.db3.network

Expand All @@ -106,24 +107,19 @@ JSON document must be signed by its owner. Only the owner can update or delete t

# What can we build with the db3 network?

1. A fully on-chain game.
2. A fully on-chain social network.

All user data will be stored permanently on the DB3 network.
Now building a fully on-chain application is an easy thing. You can create a fully on-chain game or a fully on-chain social network, or any other application you desire.

# FAQ

Q: Is the DB3 Network a blockchain?

A: No, the DB3 Network is not a blockchain. It is simply a developer tool that can be hosted locally or used through our cloud service.

Q: What are the differences between MongoDB and DB3 Network?

A: MongoDB uses centralized data storage, whereas DB3 Network uses decentralized data storage. Additionally, DB3 Network ensures that data is permanently available.

Q: Will my data be lost if the Data Rollup Node or Data Index Node is not available?

A: No, you can set up your data index node and recover your data from the blockchain.

# License

Apache License, Version 2.0
Expand Down
38 changes: 38 additions & 0 deletions java/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
target/
!.mvn/wrapper/maven-wrapper.jar
!**/src/main/**/target/
!**/src/test/**/target/

### IntelliJ IDEA ###
.idea/modules.xml
.idea/jarRepositories.xml
.idea/compiler.xml
.idea/libraries/
*.iws
*.iml
*.ipr

### Eclipse ###
.apt_generated
.classpath
.factorypath
.project
.settings
.springBeans
.sts4-cache

### NetBeans ###
/nbproject/private/
/nbbuild/
/dist/
/nbdist/
/.nb-gradle/
build/
!**/src/main/**/build/
!**/src/test/**/build/

### VS Code ###
.vscode/

### Mac OS ###
.DS_Store
37 changes: 37 additions & 0 deletions java/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
# Quick Started

the java sdk is under active development, please feel free to ask for help if you have some problems with it.

## DB3 SDK

```xml
<dependency>
<groupId>network.db3</groupId>
<artifactId>sdk</artifactId>
<version>1.0-SNAPSHOT</version>
</dependency>
```

## How to use

```java
// from web3j
ECKeyPair keyPair = Keys.createEcKeyPair();
Client client = new Client("https://rollup.cloud.db3.network", "https://index.cloud.db3.network", keyPair);
// update the nonce for the first time
client.updateNonce();
String db = "0x6ef32f0d8fc6bc872ffa977eb80920a0a75d0206";
String col = "book";
String doc = """{
"name":"The Three-Body Problem",
"author":"Cixin-Liu",
"rate":"4.8"
}""";
AddDocResult addDocResult = client.addDoc(db, col, doc);
ResultSet resultSet = client.runQuery(db, col, """/[author=Cixin-Liu]""");
```
you can the the db3 [console](https://console.cloud.db3.network/console/database/) to create a database




118 changes: 118 additions & 0 deletions java/pom.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,118 @@
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns="http://maven.apache.org/POM/4.0.0"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>

<groupId>network.db3</groupId>
<artifactId>sdk</artifactId>
<version>1.0-SNAPSHOT</version>

<properties>
<maven.compiler.source>8</maven.compiler.source>
<maven.compiler.target>8</maven.compiler.target>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
</properties>

<dependencies>
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
<version>2.0.7</version>
</dependency>

<dependency>
<groupId>io.grpc</groupId>
<artifactId>grpc-all</artifactId>
<version>1.56.1</version>
</dependency>

<dependency>
<groupId>org.mongodb</groupId>
<artifactId>bson</artifactId>
<version>4.9.1</version>
</dependency>

<dependency>
<groupId>org.web3j</groupId>
<artifactId>core</artifactId>
<version>4.9.8</version>
</dependency>
<dependency>
<groupId>org.web3j</groupId>
<artifactId>crypto</artifactId>
<version>4.9.8</version>
</dependency>
<dependency>
<groupId>commons-codec</groupId>
<artifactId>commons-codec</artifactId>
<version>1.15</version>
</dependency>
<dependency>
<groupId>com.google.code.gson</groupId>
<artifactId>gson</artifactId>
<version>2.10</version>
</dependency>

<dependency>
<groupId>javax.annotation</groupId>
<artifactId>javax.annotation-api</artifactId>
<version>1.2</version>
<scope>compile</scope>
</dependency>

</dependencies>


<build>
<extensions>
<extension>
<groupId>kr.motd.maven</groupId>
<artifactId>os-maven-plugin</artifactId>
</extension>
</extensions>
<plugins>
<plugin>
<groupId>org.xolstice.maven.plugins</groupId>
<artifactId>protobuf-maven-plugin</artifactId>
<configuration>
<!--
The version of protoc must match protobuf-java. If you don't depend on
protobuf-java directly, you will be transitively depending on the
protobuf-java version that grpc depends on.
-->
<protocArtifact>
com.google.protobuf:protoc:3.21.10:exe:${os.detected.classifier}
</protocArtifact>
<pluginId>grpc-java</pluginId>
<pluginArtifact>
io.grpc:protoc-gen-grpc-java:1.51.0:exe:${os.detected.classifier}
</pluginArtifact>
<protoSourceRoot>
${basedir}/../src/proto/proto
</protoSourceRoot>
</configuration>
<executions>
<execution>
<goals>
<goal>compile</goal>
<goal>compile-custom</goal>
</goals>
</execution>
</executions>
</plugin>

</plugins>
</build>
<distributionManagement>
<snapshotRepository>
<id>ossrh</id>
<url>https://s01.oss.sonatype.org/content/repositories/snapshots</url>
</snapshotRepository>
<repository>
<id>ossrh</id>
<url>https://s01.oss.sonatype.org/service/local/staging/deploy/maven2/</url>
</repository>
</distributionManagement>
</project>
19 changes: 19 additions & 0 deletions java/src/main/java/network/db3/client/AddDocResult.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
package network.db3.client;

public class AddDocResult {
private String mutationId;
private long docId;

public AddDocResult(String mutationId, long docId) {
this.mutationId = mutationId;
this.docId = docId;
}

public long getDocId() {
return docId;
}

public String getMutationId() {
return mutationId;
}
}
120 changes: 120 additions & 0 deletions java/src/main/java/network/db3/client/Client.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,120 @@
package network.db3.client;

import com.google.protobuf.ByteString;
import db3_database_v2_proto.Db3DatabaseV2;
import db3_indexer_proto.Db3Indexer;
import db3_indexer_proto.IndexerNodeGrpc;
import db3_mutation_v2_proto.Db3MutationV2;
import db3_storage_proto.Db3Storage;
import db3_storage_proto.StorageNodeGrpc;
import io.grpc.Grpc;
import io.grpc.ManagedChannel;
import io.grpc.ManagedChannelBuilder;
import io.grpc.TlsChannelCredentials;
import io.grpc.netty.GrpcSslContexts;
import io.netty.handler.ssl.SslContext;
import network.db3.provider.IndexProvider;
import network.db3.provider.StorageProvider;
import network.db3.store.ResultSet;
import org.bson.ByteBuf;
import org.bson.RawBsonDocument;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.web3j.crypto.ECKeyPair;
import org.web3j.crypto.Keys;
import org.web3j.utils.Numeric;

import java.io.IOException;
import java.net.MalformedURLException;
import java.net.URL;
import java.util.Optional;
import java.util.concurrent.atomic.AtomicLong;

public class Client {
private static final Logger logger = LoggerFactory.getLogger(Client.class);
private final ECKeyPair keyPair;
private final StorageProvider storageProvider;
private final IndexProvider indexProvider;
private final AtomicLong nonce;

public Client(String rollupUrl, String indexUrl,
ECKeyPair keyPair) throws MalformedURLException {
ManagedChannel rollupChannel = Client.buildFrom(rollupUrl);
ManagedChannel indexChannel = Client.buildFrom(indexUrl);
StorageNodeGrpc.StorageNodeBlockingStub rollupStub = StorageNodeGrpc.newBlockingStub(rollupChannel);
IndexerNodeGrpc.IndexerNodeBlockingStub indexStub = IndexerNodeGrpc.newBlockingStub(indexChannel);
this.storageProvider = new StorageProvider(rollupStub, keyPair);
this.indexProvider = new IndexProvider(indexStub);
this.keyPair = keyPair;
this.nonce = new AtomicLong(0);
}

private static ManagedChannel buildFrom(String url) throws MalformedURLException {
URL uri = new URL(url);
if (uri.getProtocol().equals("https")){
TlsChannelCredentials.Builder tlsBuilder = TlsChannelCredentials.newBuilder();
return Grpc.newChannelBuilderForAddress(uri.getHost(), uri.getPort() == 0 ? 443: uri.getPort(),
tlsBuilder.build()).build();
} else {
return ManagedChannelBuilder.forTarget(uri.getHost() + ":" + uri.getPort()).usePlaintext().build();
}
}

public void updateNonce() {
long nonce = this.storageProvider.getNonce(Keys.getAddress(keyPair));
this.nonce.set(nonce);
logger.info("the new nonce {} for address {}", nonce, Keys.getAddress(keyPair));
}

public CreateDBResult createDocDatabase(String desc) throws IOException {
Db3MutationV2.DocumentDatabaseMutation docMutation = Db3MutationV2.DocumentDatabaseMutation.newBuilder().setDbDesc(desc).build();
Db3MutationV2.Mutation.BodyWrapper body = Db3MutationV2.Mutation.BodyWrapper.newBuilder().setDocDatabaseMutation(docMutation).setDbAddress(ByteString.copyFromUtf8("")).build();
Db3MutationV2.Mutation mutation = Db3MutationV2.Mutation.newBuilder().setAction(Db3MutationV2.MutationAction.CreateDocumentDB).addBodies(body).build();
byte[] data = mutation.toByteArray();
long nonce = this.nonce.getAndIncrement();
Db3Storage.SendMutationResponse response = this.storageProvider.sendMutation(data, nonce);
return new CreateDBResult(response.getId(), response.getItems(0).getValue());
}

public Db3DatabaseV2.DatabaseMessage getDatabase(String db) {
Db3Storage.GetDatabaseResponse response = this.storageProvider.getDatabase(db);
return response.getDatabase();
}

public CreateCollectonResult createCollection(String db, String col) throws IOException {
byte[] address = Numeric.hexStringToByteArray(db);
Db3MutationV2.CollectionMutation collectionMutation = Db3MutationV2.CollectionMutation.newBuilder().setCollectionName(col).build();
Db3MutationV2.Mutation.BodyWrapper body = Db3MutationV2.Mutation.BodyWrapper.newBuilder().setCollectionMutation(collectionMutation).setDbAddress(ByteString.copyFrom(address)).build();
Db3MutationV2.Mutation mutation = Db3MutationV2.Mutation.newBuilder().setAction(Db3MutationV2.MutationAction.AddCollection).addBodies(body).build();
byte[] data = mutation.toByteArray();
long nonce = this.nonce.getAndIncrement();
Db3Storage.SendMutationResponse response = this.storageProvider.sendMutation(data, nonce);
return new CreateCollectonResult(response.getId());
}

public Optional<Db3DatabaseV2.Collection> getCollection(String db, String col) {
return this.storageProvider.getCollection(db, col);
}

public AddDocResult addDoc(String db, String col, String json) throws IOException {
RawBsonDocument rawBsonDocument = RawBsonDocument.parse(json);
ByteBuf buf = rawBsonDocument.getByteBuffer();
byte[] data = new byte[buf.remaining()];
buf.get(data);
Db3MutationV2.DocumentMutation documentMutation = Db3MutationV2.DocumentMutation.newBuilder().addDocuments(ByteString.copyFrom(data)).setCollectionName(col).build();
Db3MutationV2.Mutation.BodyWrapper body = Db3MutationV2.Mutation.BodyWrapper.newBuilder().setDbAddress(ByteString.copyFrom(Numeric.hexStringToByteArray(db))).setDocumentMutation(documentMutation).build();
Db3MutationV2.Mutation mutation = Db3MutationV2.Mutation.newBuilder().setAction(Db3MutationV2.MutationAction.AddDocument).addBodies(body).build();
byte[] buffer = mutation.toByteArray();
long nonce = this.nonce.getAndIncrement();
Db3Storage.SendMutationResponse response = this.storageProvider.sendMutation(buffer, nonce);
return new AddDocResult(response.getId(), Long.parseLong(response.getItems(0).getValue()));
}

public ResultSet runQuery(String db, String col, String query) {
Db3Indexer.RunQueryResponse response = this.indexProvider.runQuery(db, col, query);
ResultSet resultSet = new ResultSet();
resultSet.setDocs(response.getDocumentsList());
resultSet.setCount(response.getCount());
return resultSet;
}
}
Loading

0 comments on commit 5359790

Please sign in to comment.