Unoffical danalock web API

What is the full URL of the request?

How do you run node-red?

Hi Erik,

thank you for building this!
While i was completely new towards node-red i managed to get it working.
Maybe you can add to the manual that your lock name is case sensitive.

so when you do the api call you need to use the exact name as defined in my.danalock.com

https://blabla:1880/endpoint/danalock/bridge/Achterdeur/execute/lock

As you can see i my lock name is Achterdeur with a capital A.

Fixed in the node-red wrapper doc at github. Thanks for the feedback!

The implementation works great!
Seems like the API from dana lock is quite slow on responses. So when trying to visualize the status of the lock, I think I get some ā€œunavailableā€ responses that then gives a wrong status of the lock.

Any tips on an improvement of this?

Using the following configuration:

rest_command:
  lock_door:
    url: http://ip:1880/danalock/bridge/Hjem/execute/lock
    method: get
    timeout: 20
  unlock_door:
    url: http://ip:1880/danalock/bridge/Hjem/execute/unlock
    method: get
    timeout: 20
  status_door:
    url: http://ip:1880/danalock/bridge/Hjem/execute/status
    method: get
    timeout: 20
  battery_door:
    url: http://ip:1880/danalock/bridge/Hjem/execute/battery-level
    method: get
    timeout: 20



lock:
  - platform: template
    name: DĆør
    value_template: "{{ is_state('sensor.dorstatus', 'Locked') }}"
    lock:
      service: rest_command.lock_door
      target:
        entity_id: switch.door
    unlock:
      service: rest_command.unlock_door
      target:
        entity_id: switch.door

Hi! I donā€™t know if Danalock applies some sort of throttling on API calls. Regardless, I see you have the timeout set to 20 seconds, and that should be enough.

You can always review the node-red that iterates (loops) until the danalock has acquired status from the lock. I think it works as expected, but since youā€™re experiencing issues I get doubts.

From my personal experience, using the ā€œunlockā€ action has been working very well for months now.

HI dear community,
I need some help with the danalock nodered implementation.
I loaded the git hub flow and updated adequately the top node with username and password from danalock but impossible to run successfully one of the exposed url.
If I try to fire ā€œhttp://192.168.xxx.xxx:1880/danalock/bridge//execute/statusā€ I see a lot of error 401 in the debug window from nodered without clear explanation.
I can see my device in my.danalock dashboard, the name have no space or dash on itā€¦
Any idea?

Hi!

Have a look at the URL, you have to add the name of the lock to the URL. The below example is for a lock called storage_room

http://node-red:1880/danalock/bridge/storage_room/execute/unlock

Change your URL and try again, does it work?

Hi Erik, no unfortunately not, this is the url I used: http://my_nodered_srv_ip:1880/danalock/bridge/my_danalock_name/execute/unlock. Inside nodered I can see a lot of 401 messages comming.

Maybe I found something, I well updated the ā€œset and credentials & reset flow variablesā€ with login and password but, if I click on Inject node I can see 4 messages:

{"_msgid":"ddb70b9e4afe578c"}

{"_msgid":"ddb70b9e4afe578c"}

{"_msgid":"ddb70b9e4afe578c","oauth2Request":{"access_token_url":"https://api.danalock.com/oauth2/token","credentials":{"grant_type":"password","username":"my_username","password":"my_password","client_id":"danalock-web","client_secret":"","scope":""}}}

{"_msgid":"ddb70b9e4afe578c","payload":{"error":"invalid_request","message":"The request is missing a required parameter, includes an invalid parameter value, includes a parameter more than once, or is otherwise malformed.","hint":"one time password"}}

Maybe my issue is related with the last messageā€¦ but what is missing?
For info, for this test I import a fresh rednode json from the project github, to be sure itā€™s clean and not modified.

I get the same error and I have not managed to get around it.

Which version of nodered are you using? I noticed v3 is in the makings.

Did you install the oauth module as well?

the current nodered version I have is v2.2.2
Yes, the node-red-contrib-oauth2 v3.0.3 is installed.

I updated to node-red-contrib-oauth2 v3.0.3 and reviewed the oauth request message and it looked identical to the one @olituks provided.

Can you export your node-red flow and share it with me? I want to view it using a hex editor to see if some characters in the oauth request gets incorrectly represented due to some copy n paste poor handling of character conversion - this is a ultra long shot

Bellow the extracted flow. The only modification I made is the login and password.
the json flow

How do you run node-red?

Hi Erik, can you precise your question?
My node-red is a service setup on a RPI via these instructions (Running on Raspberry Pi : Node-RED)

I do a test with IFTTT and I get an interesting result.
IFTTT can interact with danalock, he can retrieve my device and showing his name, but if I fire a lock or unlock action I get a laconic error from danalock ā€œThere was a problem running the action.ā€

Can you test if you can interact with your danalock device and IFTTT just to get confirmation itā€™s a ā€œgeneralā€ issue or not?

The way you run it sounds good.

Can you try to acquire an access token manually? Personally I usually use postman for executing api commands.

Do you manage to retrieve an access token and refresh token?

I not succeed to get a token.
Bellow, the request without my valid login and password.

POST https://api.danalock.com/oauth2/token: {
  "Network": {
    "addresses": {
      "local": {
        "address": "172.17.0.2",
        "family": "IPv4",
        "port": 59894
      },
      "remote": {
        "address": "99.83.133.6",
        "family": "IPv4",
        "port": 443
      }
    },
    "tls": {
      "reused": false,
      "authorized": true,
      "authorizationError": null,
      "cipher": {
        "name": "ECDHE-RSA-AES128-GCM-SHA256",
        "standardName": "TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256",
        "version": "TLSv1.2"
      },
      "protocol": "TLSv1.2",
      "ephemeralKeyInfo": {
        "type": "ECDH",
        "name": "prime256v1",
        "size": 256
      },
      "peerCertificate": {
        "subject": {
          "commonName": "*.danalock.com",
          "alternativeNames": "DNS:*.danalock.com, DNS:ekey-backend-prod.pre-prod.danalock.com, DNS:*.danalockservices.com, DNS:ekey.poly-control.com"
        },
        "issuer": {
          "country": "US",
          "organization": "Amazon",
          "organizationalUnit": "Server CA 1B",
          "commonName": "Amazon"
        },
        "validFrom": "May  2 00:00:00 2022 GMT",
        "validTo": "May 31 23:59:59 2023 GMT",
        "fingerprint": "1A:56:EC:0A:64:86:BF:18:69:E1:3C:27:00:E3:C7:39:EA:96:BD:86",
        "serialNumber": "09209FF8A6246AA5BA3A4E22CB3D37CA"
      }
    }
  },
  "Request Headers": {
    "content-type": "application/x-www-form-urlencoded",
    "user-agent": "PostmanRuntime/7.29.0",
    "accept": "*/*",
    "cache-control": "no-cache",
    "postman-token": "12645f26-e7b5-4fc7-83f0-b3ab4c4ada02",
    "host": "api.danalock.com",
    "accept-encoding": "gzip, deflate, br",
    "connection": "keep-alive"
  },
  "Request Body": {
    "grant_type": "password",
    "username": "<my_username>",
    "password": "<my_password>",
    "client_id": "danalock-web",
    "client_secret": ""
  },
  "Response Headers": {
    "date": "Wed, 25 May 2022 22:04:50 GMT",
    "content-type": "application/json",
    "content-length": "212",
    "connection": "keep-alive",
    "access-control-allow-credentials": "true",
    "access-control-allow-headers": "Content-Type, Authorization, X-Assume-User",
    "access-control-allow-methods": "GET, POST, DELETE, PUT, PATCH, HEAD",
    "access-control-allow-origin": "*",
    "access-control-expose-headers": "X-Page, X-Pages, X-PerPage, X-TotalRecords, mode",
    "cache-control": "no-cache, no-store, must-revalidate",
    "expires": "0",
    "server": "nginx",
    "vary": "Origin"
  },
  "Response Body": "{\"error\":\"invalid_request\",\"message\":\"The request is missing a required parameter, includes an invalid parameter value, includes a parameter more than once, or is otherwise malformed.\",\"hint\":\"one time password\"}"
}
Error: invalid_request

Change username and password and import this to Postman

{
	"info": {
		"_postman_id": "b355effa-f715-40b1-8c29-37bc15abd47f",
		"name": "Danalock",
		"schema": "https://schema.getpostman.com/json/collection/v2.1.0/collection.json"
	},
	"item": [],
	"auth": {
		"type": "oauth2",
		"oauth2": [
			{
				"key": "password",
				"value": "mypassword",
				"type": "string"
			},
			{
				"key": "clientSecret",
				"value": "\"\"",
				"type": "string"
			},
			{
				"key": "addTokenTo",
				"value": "queryParams",
				"type": "string"
			},
			{
				"key": "client_authentication",
				"value": "header",
				"type": "string"
			},
			{
				"key": "accessTokenUrl",
				"value": "https://api.danalock.com/oauth2/token",
				"type": "string"
			},
			{
				"key": "clientId",
				"value": "danalock-web",
				"type": "string"
			},
			{
				"key": "username",
				"value": "myusername",
				"type": "string"
			},
			{
				"key": "grant_type",
				"value": "password_credentials",
				"type": "string"
			}
		]
	},
	"event": [
		{
			"listen": "prerequest",
			"script": {
				"type": "text/javascript",
				"exec": [
					""
				]
			}
		},
		{
			"listen": "test",
			"script": {
				"type": "text/javascript",
				"exec": [
					""
				]
			}
		}
	]
}

Same error

{"error":"invalid_request","message":"The request is missing a required parameter, includes an invalid parameter value, includes a parameter more than once, or is otherwise malformed.","hint":"one time password"}

I carefully copy/past your json in a text editor, adding my username and password and import the new json via the raw function from postman.

Ok, letā€™s capture traffic when you login to the Danalock web UI.

In Edge, browse to the Danalock web UI, right click and select ā€œinspectā€.

Then select ā€œnetworkā€, and further (I donā€™t remember the exact details), then login and you should see request that contain the oauth stuff.

Did you manage to capture it? If so, was it different from what you use in the nodered?