Skip to content

Commit

Permalink
Updated dependencies. Small improvements
Browse files Browse the repository at this point in the history
  • Loading branch information
erwin-kok committed Jul 27, 2023
1 parent f4acad7 commit 939351d
Show file tree
Hide file tree
Showing 10 changed files with 116 additions and 81 deletions.
57 changes: 47 additions & 10 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -40,35 +40,72 @@ Next to this, it also implements Cid: https:/multiformats/cid
This project is using the [result-monad](https:/erwin-kok/result-monad)

This means that (almost) all methods of this project return a `Result<...>`. The caller can check whether an error was generated,
or it can use the value. For example:
or it can use the value.

## Usage

A (very) brief description on how to use multiformats:

...but please also look at the various tests.

### multiaddr

```kotlin
val selected = MultistreamMuxer.selectOneOf(setOf("/a", "/b", "/c"), connection)
val addr1 = Multiaddress.fromString("/ip4/127.0.0.1/p2p/QmcgpsyWgH8Y8ajJz1Cu72KnS5uo2Aa2LpzU7kinSupNKC/tcp/1234")
.getOrElse {
log.error { "Error selecting protocol: ${errorMessage(it)}" }
log.error { "Could not parse Multiaddress: ${errorMessage(it)}" }
return Err(it)
}
val ip6Addr = Multiaddress.fromString("/ip6/2001:8a0:7ac5:4201:3ac9:86ff:fe31:7095").getOrThrow()
val tcpAddr = Multiaddress.fromString("/tcp/8000").getOrThrow()
val webAddr = Multiaddress.fromString("/ws").getOrThrow()
val actual1 = Multiaddress.fromString("/").expectNoErrors()
.encapsulate(ip6Addr).expectNoErrors()
.encapsulate(tcpAddr).expectNoErrors()
.encapsulate(webAddr).expectNoErrors()
.toString()
```

In the examples below `OnFailure` is used as a convenience, but other methods can be used as well.
### multibase

If you would like to throw the Error instead, do:
```kotlin
val multibase = Multibase.encode("base16", "foobar".toByteArray()).getOrThrow()
val bytes = Multibase.decode("f666f6f626172").getOrThrow()
```

### multicodec
```kotlin
val codec = Multicodec.nameToType("cidv2")
```

### multihash
```kotlin
val selected = MultistreamMuxer.selectOneOf(setOf("/a", "/b", "/c"), connection).getOrThrow()
val multihash = Multihash.fromBase58("QmPfjpVaf593UQJ9a5ECvdh2x17XuJYG5Yanv5UFnH3jPE")
```

### multistream-select

```kotlin
val selected = MultistreamMuxer.selectOneOf(setOf("/a", "/b", "/c"), connection)
.getOrElse {
log.error { "Error selecting protocol: ${errorMessage(it)}" }
return Err(it)
}
```

This will return the key pair when no error occurred, and throws an `Error` exception when an error occurred.

## Sub-modules

This project has three sub-modules:
This project has three submodules:

```shell
git submodule add https:/multiformats/multicodec src/main/kotlin/org/erwinkok/multiformat/spec/multicodec

git submodule add https:/multiformats/multibase src/main/kotlin/org/erwinkok/multiformat/spec/multibase

git submodule add https:/multiformats/multihash src/main/kotlin/org/erwinkok/multiformat/spec/multihash
```

These are the official specifications repositories, which are used here for auto-generation code and or verifying the
test results are according to spec.

## Contributing

Expand Down
2 changes: 1 addition & 1 deletion build.gradle.kts
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@ repositories {
}

group = "org.erwinkok.multiformat"
version = "1.0.0"
version = "1.1.0"

java {
withSourcesJar()
Expand Down
6 changes: 3 additions & 3 deletions gradle/libs.versions.toml
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
[versions]
kotlinx-coroutines = "1.7.2"
kotlinx-coroutines = "1.7.3"
kotlinx-atomicfu = "0.21.0"
kotlin-logging = "3.0.5"
kotlinx-serialization = "1.5.1"
junit-jupiter = "5.9.3"
junit-jupiter = "5.10.0"
slf4j-api = "2.0.7"

kotlin = "1.9.0"
Expand All @@ -17,7 +17,7 @@ protobuf-plugin = "0.9.3"
ipaddress = "5.4.0"
ktor = "2.3.2"

result-monad = "1.3.0"
result-monad = "1.4.0"

[libraries]
kotlinx-coroutines-core = { module = "org.jetbrains.kotlinx:kotlinx-coroutines-core", version.ref = "kotlinx-coroutines" }
Expand Down
2 changes: 1 addition & 1 deletion gradle/wrapper/gradle-wrapper.properties
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
distributionBase=GRADLE_USER_HOME
distributionPath=wrapper/dists
distributionUrl=https\://services.gradle.org/distributions/gradle-8.1.1-bin.zip
distributionUrl=https\://services.gradle.org/distributions/gradle-8.2.1-bin.zip
networkTimeout=10000
zipStoreBase=GRADLE_USER_HOME
zipStorePath=wrapper/dists
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
// Copyright (c) 2022 Erwin Kok. BSD-3-Clause license. See LICENSE file for more details.
package org.erwinkok.multiformat.multiaddress

import mu.KotlinLogging
import org.erwinkok.multiformat.multiaddress.components.Component
import org.erwinkok.multiformat.multibase.Multibase
import org.erwinkok.multiformat.multihash.Multihash
Expand All @@ -14,8 +13,6 @@ import org.erwinkok.result.getOrElse
import java.io.ByteArrayInputStream
import java.io.ByteArrayOutputStream

private val logger = KotlinLogging.logger {}

class Multiaddress private constructor(val components: List<Component>) {
private val _string: String by lazy { constructString() }
val bytes: ByteArray by lazy { constructBytes() }
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,9 +5,10 @@ import io.ktor.util.collections.ConcurrentSet
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.Job
import kotlinx.coroutines.launch
import mu.KotlinLogging
import org.erwinkok.result.Err
import org.erwinkok.result.Error
import org.erwinkok.result.Errors
import org.erwinkok.result.Errors.EndOfStream
import org.erwinkok.result.Ok
import org.erwinkok.result.Result
import org.erwinkok.result.getOrElse
Expand All @@ -16,6 +17,8 @@ import org.erwinkok.result.onFailure
import org.erwinkok.result.onSuccess
import java.util.Random

private val logger = KotlinLogging.logger {}

class MultistreamMuxer<T : Utf8Connection> {
private val handlers = ConcurrentSet<ProtocolHandlerInfo<T>>()

Expand All @@ -27,7 +30,7 @@ class MultistreamMuxer<T : Utf8Connection> {
val result = mutableListOf<String>()
val token = readNextToken(connection)
.getOrElse {
if (it == Errors.EndOfStream) {
if (it == EndOfStream) {
return Ok(result)
}
return Err(it)
Expand All @@ -48,6 +51,9 @@ class MultistreamMuxer<T : Utf8Connection> {
while (true) {
val nextToken = readNextToken(connection)
.getOrElse {
if (it == EndOfStream) {
return Err(ErrEndNegotiating)
}
return Err(it)
}
if (nextToken == LS) {
Expand All @@ -57,6 +63,7 @@ class MultistreamMuxer<T : Utf8Connection> {
} else {
val handler = findHandler(nextToken)
if (handler == null) {
logger.debug { "MultistreamMuxer: We do not support requested protocol $nextToken" }
connection.writeUtf8(NA)
.onFailure { return Err(it) }
} else {
Expand Down Expand Up @@ -103,7 +110,7 @@ class MultistreamMuxer<T : Utf8Connection> {
}

private fun findHandler(token: String): ProtocolHandlerInfo<T>? {
val protocol = ProtocolId.from(token)
val protocol = ProtocolId.of(token)
for (handler in handlers) {
if (handler.match(protocol)) {
return handler
Expand All @@ -127,9 +134,10 @@ class MultistreamMuxer<T : Utf8Connection> {
private const val initiator = "initiator"
private const val responder = "responder"

private val ErrIncorrectVersion = Error("client connected with incorrect version")
private val ErrNoProtocols = Error("no protocols specified")
private val ErrNotSupported = Error("Peer does not support any of the given protocols")
private val ErrIncorrectVersion = Error("client connected with incorrect version")
private val ErrEndNegotiating = Error("end negotiating: we do not support any of the requested protocols")

suspend fun selectOneOf(protocols: Set<ProtocolId>, connection: Utf8Connection): Result<ProtocolId> {
if (protocols.isEmpty()) {
Expand Down Expand Up @@ -245,7 +253,7 @@ class MultistreamMuxer<T : Utf8Connection> {
while (true) {
val nextToken = readNextToken(connection)
.getOrElse {
if (it == Errors.EndOfStream) {
if (it == EndOfStream) {
return Err(ErrNotSupported)
}
return Err(it)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@ class ProtocolId private constructor(val id: String) {

val Null = ProtocolId(UnknownProtocolId)

fun from(key: String?): ProtocolId {
fun of(key: String?): ProtocolId {
if (key.isNullOrBlank() || key == UnknownProtocolId) {
return Null
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -19,21 +19,14 @@ internal class MultihashTest {
private val MaxVarintLen64 = 10

@Test
fun toB58String() {
fun base58String() {
val src = "QmPfjpVaf593UQJ9a5ECvdh2x17XuJYG5Yanv5UFnH3jPE"
val expected = Hex.decode("122013bf801597d74a660453412635edd8c34271e5998f801fac5d700c6ce8d8e461").expectNoErrors()
val multihash = Multihash.fromBase58(src).expectNoErrors()
assertArrayEquals(multihash.bytes(), expected)
assertEquals(src, multihash.base58())
}

@Test
fun fromB58String() {
val src = "QmPfjpVaf593UQJ9a5ECvdh2x17XuJYG5Yanv5UFnH3jPE"
val expected = Hex.decode("122013bf801597d74a660453412635edd8c34271e5998f801fac5d700c6ce8d8e461").expectNoErrors()
assertArrayEquals(Multihash.fromBase58(src).expectNoErrors().bytes(), expected)
}

@Test
fun encodeName() {
val digest = Hex.decode("0beec7b5ea3f0fdbc95d0dd47f3c5bc275da8a33").expectNoErrors()
Expand Down
Loading

0 comments on commit 939351d

Please sign in to comment.