Skip to content

Commit

Permalink
Fix/e2e test fixes (#381)
Browse files Browse the repository at this point in the history
* test(shared): e2e test fix, add role to connection data class

* test(shared): e2e test fix, use valid ServiceType

* test(shared): e2e test fix, check for role in step

* test(shared): e2e test fix, use different schema names for each schema created

* test(shared): e2e test change, expect 422 results for bad properties

* test(shared): e2e test change, support PRISM DID Issuer flow

* chore(shared): remove unused containers, stop always running db, apisix

* test(shared): fix indentation according to gherkin-lint

* test(shared): fix indentation in docker-compose

* test(shared): skip failing test until fixed
  • Loading branch information
davidpoltorak-io authored Feb 21, 2023
1 parent 06cf7cf commit 2f60f22
Show file tree
Hide file tree
Showing 15 changed files with 151 additions and 131 deletions.
33 changes: 7 additions & 26 deletions infrastructure/shared/docker-compose.yml
Original file line number Diff line number Diff line change
@@ -1,13 +1,12 @@
version: '3.8'
---
version: "3.8"

services:

##########################
# Database
##########################
db:
image: postgres:13
restart: always
environment:
POSTGRES_MULTIPLE_DATABASES: "castor,pollux,connect,iris,agent,node_db"
POSTGRES_USER: postgres
Expand All @@ -27,9 +26,9 @@ services:
environment:
PGADMIN_DEFAULT_EMAIL: ${PGADMIN_DEFAULT_EMAIL:[email protected]}
PGADMIN_DEFAULT_PASSWORD: ${PGADMIN_DEFAULT_PASSWORD:-admin}
PGADMIN_CONFIG_SERVER_MODE: 'False'
PGADMIN_CONFIG_SERVER_MODE: "False"
volumes:
- pgadmin:/var/lib/pgadmin
- pgadmin:/var/lib/pgadmin
ports:
- "${PGADMIN_PORT:-5050}:80"
depends_on:
Expand All @@ -41,22 +40,6 @@ services:
##########################
# Services
##########################
mediator:
image: ghcr.io/input-output-hk/mercury-mediator:${MERCURY_MEDIATOR_VERSION}
depends_on:
db:
condition: service_healthy

iris:
image: ghcr.io/input-output-hk/iris-service:${IRIS_SERVICE_VERSION}
environment:
IRIS_DB_HOST: db
IRIS_DB_PORT: 5432
IRIS_DB_NAME: iris
IRIS_DB_USER: postgres
depends_on:
db:
condition: service_healthy

prism-node:
image: ghcr.io/input-output-hk/prism-node:${PRISM_NODE_VERSION}
Expand Down Expand Up @@ -100,7 +83,7 @@ services:
prism-node:
condition: service_started
healthcheck:
test: [ "CMD", "curl", "-f", "http://prism-agent:8080/connections" ]
test: ["CMD", "curl", "-f", "http://prism-agent:8080/connections"]
interval: 30s
timeout: 10s
retries: 5
Expand All @@ -111,20 +94,18 @@ services:
image: swaggerapi/swagger-ui:v4.14.0
environment:
- 'URLS=[
{ name: "Prism Agent", url: "/prism-agent/api/openapi-spec.yaml" },
{ name: "Mediator", url: "/mediator/api/openapi-spec.yaml" }
{ name: "Prism Agent", url: "/prism-agent/api/openapi-spec.yaml" },
{ name: "Mediator", url: "/mediator/api/openapi-spec.yaml" }
]'

apisix:
image: apache/apisix:2.15.0-alpine
restart: always
volumes:
- ./apisix/conf/apisix.yaml:/usr/local/apisix/conf/apisix.yaml:ro
- ./apisix/conf/config.yaml:/usr/local/apisix/conf/config.yaml:ro
ports:
- "${PORT}:9080/tcp"
depends_on:
- mediator
- prism-agent
- swagger-ui

Expand Down
3 changes: 2 additions & 1 deletion tests/e2e-tests/src/main/kotlin/api_models/Connection.kt
Original file line number Diff line number Diff line change
Expand Up @@ -10,5 +10,6 @@ data class Connection(
var state: String = "",
var label: String = "",
var myDid: String = "",
var theirDid: String = ""
var theirDid: String = "",
var role: String = "",
)
4 changes: 3 additions & 1 deletion tests/e2e-tests/src/main/kotlin/api_models/Credential.kt
Original file line number Diff line number Diff line change
Expand Up @@ -12,5 +12,7 @@ data class Credential(
var updatedAt: String = "",
var validityPeriod: Int = 0,
var claims: LinkedHashMap<String,String> = LinkedHashMap(),
var jwtCredential: String = ""
var jwtCredential: String = "",
var issuingDID: String = "",
var connectionId: String = ""
)
10 changes: 6 additions & 4 deletions tests/e2e-tests/src/main/kotlin/api_models/DidDocument.kt
Original file line number Diff line number Diff line change
Expand Up @@ -6,21 +6,22 @@ data class DidDocument(
)

data class W3cCompatibleDid(
var assertionMethod: List<String>? = null,
var assertionMethod: List<DidDocumentAuthentication>? = null,
var authentication: List<DidDocumentAuthentication>? = null,
var capabilityInvocation: List<String>? = null,
var controller: String? = null,
var id: String? = null,
var keyAgreement: List<String>? = null,
var service: List<DidDocumentService>? = null,
var verificationMethod: List<String>? = null
var verificationMethod: List<DidDocumentAuthentication>? = null
)

data class DidDocumentAuthentication(
var controller: String? = null,
var id: String? = null,
var publicKeyJwk: PublicKeyJwk? = null,
var type: String? = null
var type: String? = null,
var uri: String? = null
)

data class PublicKeyJwk(
Expand All @@ -31,7 +32,8 @@ data class PublicKeyJwk(
)

data class DidDocumentMetadata(
var deactivated: String? = null
var canonicalId: String? = null,
var deactivated: Boolean? = null
)

data class DidDocumentService(
Expand Down
10 changes: 10 additions & 0 deletions tests/e2e-tests/src/test/kotlin/common/CredentialSchemas.kt
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,16 @@ package common
import api_models.CredentialSchema

object CredentialSchemas {
fun generate_with_name_suffix(suffix: String): CredentialSchema {
return CredentialSchema(
author = "University",
name = "Student schema $suffix",
description = "Simple student credentials schema",
attributes = listOf("name", "age"),
tags = listOf("school", "students"),
version = "1.0"
)
}
val STUDENT_SCHEMA = CredentialSchema(
author = "University",
name = "Student schema",
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@ class ConnectionSteps {
response.body("invitation", notNullValue())
response.body("label", containsString(connectionLabel))
response.body("state", containsString("InvitationGenerated"))
response.body("role", containsString("Inviter"))
}
)
// Acme remembers invitation URL to send it out of band to Bob
Expand Down Expand Up @@ -89,6 +90,7 @@ class ConnectionSteps {
response.body("invitation.invitationUrl", containsString(acmeInvitation.invitationUrl))
response.body("invitation.type", containsString(acmeInvitation.type))
response.body("state", containsString("ConnectionRequestPending"))
response.body("role", containsString("Invitee"))
}
)
invitee.remember("connectionId", lastResponseObject("", Connection::class).connectionId)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -53,11 +53,11 @@ class CredentialSchemasSteps {
@When("{actor} creates {int} new schemas")
fun acmeCreatesMultipleSchemas(actor: Actor, numberOfSchemas: Int) {
val createdSchemas: MutableList<CredentialSchema> = mutableListOf()
repeat(numberOfSchemas) {
repeat(numberOfSchemas) { i: Int ->
actor.attemptsTo(
Post.to("/schema-registry/schemas")
.with {
it.body(TestConstants.CREDENTIAL_SCHEMAS.STUDENT_SCHEMA)
it.body(TestConstants.CREDENTIAL_SCHEMAS.generate_with_name_suffix(i.toString()))
}
)
actor.should(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -102,7 +102,7 @@ class ManageDidSteps {

private fun createManagedDidRequest(): CreateManagedDidRequest {
val publicKeys = listOf(PublicKey("123", Purpose.AUTHENTICATION))
val services = listOf(Service("did:prism:321", "MediatorService", listOf("https://foo.bar.com")))
val services = listOf(Service("did:prism:321", "LinkedDomains", listOf("https://foo.bar.com")))
val documentTemplate = DocumentTemplate(publicKeys, services)
return CreateManagedDidRequest(documentTemplate)
}
Expand Down
24 changes: 17 additions & 7 deletions tests/e2e-tests/src/test/kotlin/features/did/PublishDidSteps.kt
Original file line number Diff line number Diff line change
Expand Up @@ -20,9 +20,9 @@ import java.time.Duration
class PublishDidSteps {

@Given("{actor} creates unpublished DID")
fun acmeCreatesUnpublishedDid(acme: Actor) {
val publicKeys = listOf(PublicKey("key1", Purpose.AUTHENTICATION))
val services = listOf(Service("https://foo.bar.com", "MediatorService", listOf("https://foo.bar.com")))
fun createsUnpublishedDid(acme: Actor) {
val publicKeys = listOf(PublicKey("key1", Purpose.AUTHENTICATION), PublicKey("key2", Purpose.ASSERTION_METHOD))
val services = listOf(Service("https://foo.bar.com", "LinkedDomains", listOf("https://foo.bar.com")))
val documentTemplate = DocumentTemplate(publicKeys, services)
acme.attemptsTo(
Post.to("/did-registrar/dids")
Expand Down Expand Up @@ -90,6 +90,7 @@ class PublishDidSteps {

@Then("{actor} resolves DID document corresponds to W3C standard")
fun heSeesDidDocumentCorrespondsToW3cStandard(acme: Actor) {

val didDocument = lastResponseObject("", DidDocument::class).did!!
assertThat(didDocument)
.hasFieldOrProperty("assertionMethod")
Expand All @@ -101,12 +102,21 @@ class PublishDidSteps {
.hasFieldOrProperty("service")
.hasFieldOrProperty("verificationMethod")

assertThat(didDocument.id == acme.recall<String>("shortFormDid"))
val shortFormDid = acme.recall<String>("shortFormDid")

assertThat(didDocument.id == shortFormDid)

assertThat(didDocument.authentication!![0])
.hasFieldOrPropertyWithValue("type", "REFERENCED")
.hasFieldOrPropertyWithValue("uri", "${shortFormDid}#key1")

assertThat(didDocument.authentication!![0].publicKeyJwk)
.hasNoNullFieldsOrProperties()
assertThat(didDocument.verificationMethod!![0])
.hasFieldOrPropertyWithValue("controller", shortFormDid)
.hasFieldOrPropertyWithValue("id", "${shortFormDid}#key1")
.hasFieldOrProperty("publicKeyJwk")

assertThat(lastResponseObject("", DidDocument::class).metadata!!)
.hasFieldOrPropertyWithValue("deactivated", "false")
.hasFieldOrPropertyWithValue("deactivated", false)
.hasFieldOrProperty("canonicalId")
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -20,14 +20,16 @@ class IssueCredentialsSteps {
fun acmeOffersACredential(issuer: Actor, holder: Actor) {
val newCredential = Credential(
schemaId = "schema:1234",
subjectId = issuer.recall<Connection>("connection-with-${holder.name}").theirDid,
subjectId = holder.recall<String>("shortFormDid"),
validityPeriod = 3600,
automaticIssuance = false,
awaitConfirmation = false,
claims = linkedMapOf(
"firstName" to "FirstName",
"lastName" to "LastName"
)
),
issuingDID = issuer.recall<String>("shortFormDid"),
connectionId = issuer.recall<Connection>("connection-with-${holder.name}").connectionId
)

issuer.attemptsTo(
Expand All @@ -45,7 +47,7 @@ class IssueCredentialsSteps {
// TODO: add check that newCredential object corresponds to the output of restapi call here
}

@When("{actor} requests the credential")
@When("{actor} receives the credential offer and accepts")
fun bobRequestsTheCredential(holder: Actor) {
wait(
{
Expand All @@ -57,12 +59,12 @@ class IssueCredentialsSteps {
it.statusCode(SC_OK)
}
)
lastResponseList("items", Credential::class).findLast { it.protocolState == "OfferReceived" } != null
lastResponseList("contents", Credential::class).findLast { it.protocolState == "OfferReceived" } != null
},
"Holder was unable to receive the credential offer from Issuer! Protocol state did not achieve OfferReceived state."
)

val recordId = lastResponseList("items", Credential::class)
val recordId = lastResponseList("contents", Credential::class)
.findLast { it.protocolState == "OfferReceived" }!!.recordId
holder.remember("recordId", recordId)

Expand All @@ -88,12 +90,12 @@ class IssueCredentialsSteps {
it.statusCode(SC_OK)
}
)
lastResponseList("items", Credential::class)
lastResponseList("contents", Credential::class)
.findLast { it.protocolState == "RequestReceived" } != null
},
"Issuer was unable to receive the credential request from Holder! Protocol state did not achieve RequestReceived state."
)
val recordId = lastResponseList("items", Credential::class)
val recordId = lastResponseList("contents", Credential::class)
.findLast { it.protocolState == "RequestReceived" }!!.recordId
issuer.attemptsTo(
Post.to("/issue-credentials/records/${recordId}/issue-credential")
Expand All @@ -120,7 +122,7 @@ class IssueCredentialsSteps {
)
}

@Then("{actor} has the credential issued")
@Then("{actor} receives the issued credential")
fun bobHasTheCredentialIssued(holder: Actor) {
wait(
{
Expand Down
Original file line number Diff line number Diff line change
@@ -1,12 +1,12 @@
@RFC0160 @AIP10
Feature: Agents connection

Scenario: Establish a connection between two agents
When Acme generates a connection invitation to Bob
And Bob receives the connection invitation from Acme
And Bob sends a connection request to Acme
And Acme receives the connection request
And Acme sends a connection response to Bob
And Bob receives the connection response
# And Bob sends <message> to Acme
Then Acme and Bob have a connection
Scenario: Establish a connection between two agents
When Acme generates a connection invitation to Bob
And Bob receives the connection invitation from Acme
And Bob sends a connection request to Acme
And Acme receives the connection request
And Acme sends a connection response to Bob
And Bob receives the connection response
# And Bob sends <message> to Acme
Then Acme and Bob have a connection
Original file line number Diff line number Diff line change
@@ -1,36 +1,39 @@
Feature: Credential schemas

Scenario: Successful schema creation
When Acme creates a new credential schema
Then He sees new credential schema is available
Scenario: Successful schema creation
When Acme creates a new credential schema
Then He sees new credential schema is available

Scenario Outline: Multiple schema creation
When Acme creates <schemas> new schemas
Then He can access all of them one by one
Examples:
| schemas |
| 4 |
Scenario Outline: Multiple schema creation
When Acme creates <schemas> new schemas
Then He can access all of them one by one
Examples:
| schemas |
| 4 |

Scenario Outline: Wrong specified fields for schema generation requests should fail
When Acme tries to create a new schema with <value> in field <field>
Then He sees the request with status <status>
Examples:
| field | value | status |
| id | -1 | 400 |
| attributes | null | 400 |
Scenario Outline: Wrong specified fields for schema generation requests should fail
When Acme tries to create a new schema with <value> in field <field>
Then He sees the request with status <status>
Examples:
| field | value | status |
| id | -1 | 400 |
| attributes | null | 400 |

@skip @bug
Scenario: Schema creation with identical id should fail
When Acme creates a new schema with some id
And Acme tries to create a new schema with identical id
Then He sees the request failure with identical id error
@skip
Scenario: Schema creation with identical name should fail

@skip @bug
Scenario Outline: Wrong specified filter parameters for schema generation requests should fail
When Acme tries to get schemas with <value> in parameter <parameter>
Then He sees the request with status <status>
Examples:
| parameter | value | status |
| limit | -1 | 400 |
| offset | -1 | 400 |
| offset | 1000000 | 400 |
@skip @bug
Scenario: Schema creation with identical id should fail
When Acme creates a new schema with some id
And Acme tries to create a new schema with identical id
Then He sees the request failure with identical id error

@skip @bug
Scenario Outline: Using incorrect filter params should result in error
When Acme tries to get schemas with <value> in parameter <parameter>
Then He sees the request with status <status>
Examples:
| parameter | value | status |
| limit | -1 | 400 |
| offset | -1 | 400 |
| offset | 1000000 | 400 |
Loading

0 comments on commit 2f60f22

Please sign in to comment.