From 9eeded8a15b7393d4946ab2373ff10bee6de7d9c Mon Sep 17 00:00:00 2001 From: Akiff Manji Date: Sun, 9 Feb 2020 10:37:06 -0800 Subject: [PATCH 1/4] Updates Aries OpenAPI Demo `Establish a Connection` documentation when `--no-auto` option is enabled. See https://github.com/hyperledger/aries-cloudagent-python/issues/361 for more details. Signed-off-by: Akiff Manji --- demo/AriesOpenAPIDemo.md | 24 ++++++++++++++++++++---- demo/runners/alice.py | 2 +- demo/runners/faber.py | 5 ++++- 3 files changed, 25 insertions(+), 6 deletions(-) diff --git a/demo/AriesOpenAPIDemo.md b/demo/AriesOpenAPIDemo.md index 55b8ea93a7..b4e5de269e 100644 --- a/demo/AriesOpenAPIDemo.md +++ b/demo/AriesOpenAPIDemo.md @@ -132,15 +132,31 @@ Enough with the preliminaries, let’s get started! We’ll start the demo by establishing a connection between the Alice and Faber agents. We’re starting there to demonstrate that you can use agents without having a ledger. We won’t be using the Indy public ledger at all for this step. Since the agents communicate using DIDcomm messaging and connect by exchanging pairwise DIDs and DIDDocs based on the `did:peer` DID method, a public ledger is not needed. -In the Faber browser tab, execute the **`POST /connections/create-invitation`**. No input data is needed to be added for this call. If successful, you should see a connection ID, an invitation, and the invitation URL. The IDs will be different on each run. +In the Faber browser tab, execute the **`POST /connections/create-invitation`** endpoint. No input data is needed to be added for this call. If successful, you should see a connection ID, an invitation, and the invitation URL. The IDs will be different on each run. Copy the entire block of the `invitation` object, from the curly brackets `{}`, excluding the trailing comma. -Switch to the Alice browser tab and get ready to execute the **`POST /connections/receive-invitation`** section. Select all of the pre-populated text and replace it with the invitation object from the Faber tab. When you click `Execute` a you should get back a connection ID, an invitation key, and the state of the connection, which should be `requested`. +Before switching over to the Alice browser tab, scroll to and execute the **`GET /connections`** endpoint to see the list of Faber's connections. You should see a connection with a `connection_id` that is identical to the invitation you just created, and that its state is `invitation`. -Scroll to and execute **`GET /connections`** to see a list of Alice's connections, and the information tracked about each connection. You should see the one connection Alice’s agent has, that it is with the Faber agent, and that its status is `active`. +Switch to the Alice browser tab and get ready to execute the **`POST /connections/receive-invitation`** endpoint. Select all of the pre-populated text and replace it with the invitation object from the Faber tab. When you click `Execute` you should get back a connection response with a connection ID, an invitation key, and the state of the connection, which should be `request`. -You are connected! Switch to the Faber agent browser tab and run the same **`GET /connections`** endpoint to see Faber view of the connection. Hint - note the `connection_id`. You’ll need it later in the tutorial. +> **Establishing connections with `--no-auto`** + +> If you started agents with the `--no-auto` option there are few more steps required to complete the connection between Alice and Faber. _If you started agents with the default options, skip this section, these intermediate steps are automated (see the [notes](#notes) below for what is actually happening behind the scenes)._ + +> The connection response returned from the previous **`POST /connections/receive-invitation`** endpoint call will currently show a connection state of `invitation` rather than `request`. + +> At this point Alice has simply stored the invitation in her wallet. To complete a connection with Faber, she must accept the invitation and send a corresponding connection request to Faber. Find the `connection_id` in the connection response from the previous **`POST /connections/receive-invitation`** endpoint call. Scroll to the **`POST /connections/{id}/accept-invitation`** endpoint and paste the `connection_id` in the `id` parameter field (you will have to click the `Try it out` button to see the available URL parameters). The response from clicking `Execute` should show that the connection has a state of `request`. + +> Switch over to the Faber broswer tab, scroll to and execute the **`GET /connections`** endpoint. Note the connection that was previously created. It's state is now `request`, which indicates that Alice has accepted the invitation and has sent a corresponding connection request to Faber. Copy the `connection_id` for the next step. + +> To complete the connection process, Faber will respond to the connection request from Alice. Scroll to the **`POST /connections/{id}/accept-request`** endpint and paste the `connection_id` you previously copied into the `id` parameter field (you will have to click the `Try it out` button to see the available URL parameters). The response from clicking the `Execute` button should show that the connection has a state of `response`, which indicates that Faber has accepted Alice's connection request. + +> Switch over the the Alice browser tab. + +Scroll to and execute **`GET /connections`** to see a list of Alice's connections, and the information tracked about each connection. You should see the one connection Alice’s agent has, that it is with the Faber agent, and that its state is `active`. + +You are connected! Switch to the Faber browser tab and run the same **`GET /connections`** endpoint to see Faber's view of the connection. Its state is also `active`. Note the `connection_id`, you’ll need it later in the tutorial. ### Notes diff --git a/demo/runners/alice.py b/demo/runners/alice.py index 847dd186a0..8e87da9872 100644 --- a/demo/runners/alice.py +++ b/demo/runners/alice.py @@ -34,7 +34,7 @@ def __init__(self, http_port: int, admin_port: int, **kwargs): extra_args=[ "--auto-accept-invites", "--auto-accept-requests", - "--auto-store-credential", + "--auto-store-credential" ], seed=None, **kwargs, diff --git a/demo/runners/faber.py b/demo/runners/faber.py index 7dd8131147..1585e79fed 100644 --- a/demo/runners/faber.py +++ b/demo/runners/faber.py @@ -34,7 +34,10 @@ def __init__(self, http_port: int, admin_port: int, **kwargs): http_port, admin_port, prefix="Faber", - extra_args=["--auto-accept-invites", "--auto-accept-requests"], + extra_args=[ + "--auto-accept-invites", + "--auto-accept-requests" + ], **kwargs, ) self.connection_id = None From 5a924a50a227ac59a87c6eb90dfb49f2907ae4f4 Mon Sep 17 00:00:00 2001 From: Akiff Manji Date: Sat, 15 Feb 2020 18:06:08 -0800 Subject: [PATCH 2/4] Adds EVENT `logger` instance to `agent.py` Will display: Agent API requests with method, path and request body (pretty printed) Agent API responses with method, path and response body (pretty printed) Controller webhook calls with handler name and payload (pretty printed) See https://github.com/hyperledger/aries-cloudagent-python/issues/361 for more details. Signed-off-by: Akiff Manji --- demo/runners/support/agent.py | 18 ++++++++++++++++-- 1 file changed, 16 insertions(+), 2 deletions(-) diff --git a/demo/runners/support/agent.py b/demo/runners/support/agent.py index 4765273136..c1429819fc 100644 --- a/demo/runners/support/agent.py +++ b/demo/runners/support/agent.py @@ -21,6 +21,14 @@ LOGGER = logging.getLogger(__name__) +event_stream_handler = logging.StreamHandler() +event_stream_handler.setFormatter(logging.Formatter("\nEVENT: %(message)s")) + +EVENT_LOGGER = logging.getLogger('event') +EVENT_LOGGER.setLevel(logging.DEBUG) +EVENT_LOGGER.addHandler(event_stream_handler) +EVENT_LOGGER.propagate = False + DEFAULT_POSTGRES = bool(os.getenv("POSTGRES")) DEFAULT_INTERNAL_HOST = "127.0.0.1" DEFAULT_EXTERNAL_HOST = "localhost" @@ -330,6 +338,7 @@ async def handle_webhook(self, topic: str, payload): handler = f"handle_{topic}" method = getattr(self, handler, None) if method: + EVENT_LOGGER.debug(f"Agent called controller webhook: {handler}" + f" with payload: \n{json.dumps(payload, indent=4)}" if payload else "") asyncio.get_event_loop().create_task(method(payload)) else: log_msg( @@ -358,7 +367,9 @@ async def admin_request( async def admin_GET(self, path, text=False, params=None) -> ClientResponse: try: - return await self.admin_request("GET", path, None, text, params) + EVENT_LOGGER.debug(f"Controller GET {path} request to Agent") + response = await self.admin_request("GET", path, None, text, params) + EVENT_LOGGER.debug(f"Response from GET {path} received: \n{json.dumps(response, indent=4)}") except ClientError as e: self.log(f"Error during GET {path}: {str(e)}") raise @@ -367,7 +378,10 @@ async def admin_POST( self, path, data=None, text=False, params=None ) -> ClientResponse: try: - return await self.admin_request("POST", path, data, text, params) + EVENT_LOGGER.debug(f"Controller POST {path} request to Agent" + f" with data: \n{json.dumps(data, indent=4)}" if data else ""); + response = await self.admin_request("POST", path, data, text, params) + EVENT_LOGGER.debug(f"Response from POST {path} received: \n{json.dumps(response, indent=4)}"); + return response except ClientError as e: self.log(f"Error during POST {path}: {str(e)}") raise From 37f67c10b2fa5c8df49100decbda152b48b6e47c Mon Sep 17 00:00:00 2001 From: Akiff Manji Date: Sat, 15 Feb 2020 18:54:40 -0800 Subject: [PATCH 3/4] Adds environment variable for `--events` option in `run_demo`` Will enable event logging in Cloudagent Signed-off-by: Akiff Manji --- demo/run_demo | 19 +++++++++++++++++-- demo/runners/support/agent.py | 2 +- 2 files changed, 18 insertions(+), 3 deletions(-) diff --git a/demo/run_demo b/demo/run_demo index 6627b8a7d2..390c4c5a68 100755 --- a/demo/run_demo +++ b/demo/run_demo @@ -4,8 +4,19 @@ shopt -s nocasematch cd $(dirname $0) -AGENT="$1" -shift +for i in "$@" +do + case $i in + -e|--events) + EVENTS=1 + shift + ;; + *) + AGENT="$i" + shift + ;; + esac +done case "$@" in *--timing*) if [ ! -d "../logs" ]; then @@ -75,6 +86,10 @@ if ! [ -z "$GENESIS_URL" ]; then DOCKER_ENV="${DOCKER_ENV} -e GENESIS_URL=${GENESIS_URL}" fi +if ! [ -z "$EVENTS" ]; then + DOCKER_ENV="${DOCKER_ENV} -e EVENTS=1" +fi + # on Windows, docker run needs to be prefixed by winpty if [ "$OSTYPE" = "msys" ]; then DOCKER="winpty docker" diff --git a/demo/runners/support/agent.py b/demo/runners/support/agent.py index c1429819fc..3215dff66a 100644 --- a/demo/runners/support/agent.py +++ b/demo/runners/support/agent.py @@ -25,7 +25,7 @@ event_stream_handler.setFormatter(logging.Formatter("\nEVENT: %(message)s")) EVENT_LOGGER = logging.getLogger('event') -EVENT_LOGGER.setLevel(logging.DEBUG) +EVENT_LOGGER.setLevel(logging.DEBUG if os.getenv("EVENTS") else logging.NOTSET) EVENT_LOGGER.addHandler(event_stream_handler) EVENT_LOGGER.propagate = False From 0e420f76d4000f74a2a932ca5bbd9cf5fdbf23c2 Mon Sep 17 00:00:00 2001 From: Akiff Manji Date: Sat, 15 Feb 2020 19:23:25 -0800 Subject: [PATCH 4/4] Adds `--no-auto` option to `run_demo` that deactivates `--auto-...` options in agents. Signed-off-by: Akiff Manji --- demo/run_demo | 9 ++++++++- demo/runners/alice.py | 2 +- demo/runners/faber.py | 2 +- demo/runners/support/agent.py | 2 +- 4 files changed, 11 insertions(+), 4 deletions(-) diff --git a/demo/run_demo b/demo/run_demo index 390c4c5a68..6650be5716 100755 --- a/demo/run_demo +++ b/demo/run_demo @@ -7,10 +7,14 @@ cd $(dirname $0) for i in "$@" do case $i in - -e|--events) + --events) EVENTS=1 shift ;; + --no-auto) + NO_AUTO=1 + shift + ;; *) AGENT="$i" shift @@ -89,6 +93,9 @@ fi if ! [ -z "$EVENTS" ]; then DOCKER_ENV="${DOCKER_ENV} -e EVENTS=1" fi +if ! [ -z "$NO_AUTO" ]; then + DOCKER_ENV="${DOCKER_ENV} -e NO_AUTO=1" +fi # on Windows, docker run needs to be prefixed by winpty if [ "$OSTYPE" = "msys" ]; then diff --git a/demo/runners/alice.py b/demo/runners/alice.py index 8e87da9872..8cfd5b2352 100644 --- a/demo/runners/alice.py +++ b/demo/runners/alice.py @@ -31,7 +31,7 @@ def __init__(self, http_port: int, admin_port: int, **kwargs): http_port, admin_port, prefix="Alice", - extra_args=[ + extra_args=[] if os.getenv("NO_AUTO") else [ "--auto-accept-invites", "--auto-accept-requests", "--auto-store-credential" diff --git a/demo/runners/faber.py b/demo/runners/faber.py index 1585e79fed..2bd60e9bbe 100644 --- a/demo/runners/faber.py +++ b/demo/runners/faber.py @@ -34,7 +34,7 @@ def __init__(self, http_port: int, admin_port: int, **kwargs): http_port, admin_port, prefix="Faber", - extra_args=[ + extra_args=[] if os.getenv("NO_AUTO") else [ "--auto-accept-invites", "--auto-accept-requests" ], diff --git a/demo/runners/support/agent.py b/demo/runners/support/agent.py index 3215dff66a..cbc76e36f7 100644 --- a/demo/runners/support/agent.py +++ b/demo/runners/support/agent.py @@ -24,7 +24,7 @@ event_stream_handler = logging.StreamHandler() event_stream_handler.setFormatter(logging.Formatter("\nEVENT: %(message)s")) -EVENT_LOGGER = logging.getLogger('event') +EVENT_LOGGER = logging.getLogger("event") EVENT_LOGGER.setLevel(logging.DEBUG if os.getenv("EVENTS") else logging.NOTSET) EVENT_LOGGER.addHandler(event_stream_handler) EVENT_LOGGER.propagate = False