Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Feature Request: Make Client Requests from One Device to Another Device #152

Open
mriksman opened this issue Jun 19, 2020 · 2 comments
Open

Comments

@mriksman
Copy link
Contributor

Hey,

RavenSystem's esp-homekit-devices allows unencrypted client commands by simply modifying these lines https://github.com/RavenSystem/esp-homekit-devices/blob/master/external_libs/homekit/src/server.c#L2984.

You can then send standard unencrypted HTTP URL like

curl -X PUT -d '{"characteristics":[{"aid":1,"iid":9,"value":true}]}' http://device_ip_address:5556/characteristic

Is it possible to have a function in esp-homekit to send an encrypted command to another esp-homekit device?

Use-case; 2-way light switch. Configure one light switch's callback function to send a HTTP PUT request to another esp-homekit device.

@beckmx
Copy link

beckmx commented Jun 22, 2020

You would need to modify the server, as in raven, there is a function around there that I remember gives you the unencrypted result of the message, however keep in mind that what you want might be a bridge, a device that links several devices inside. You can also use the mdns service to track devices with the same descriptio. I personally implemented this by opening another connection, (unencrypted) to avoid modifying the core more than what I needed to.

@mriksman
Copy link
Contributor Author

mriksman commented Jun 23, 2020

I modified the following lines

esp-homekit/src/server.c

Lines 2936 to 2984 in 9824dc5

if (!context->encrypted) {
switch(context->endpoint) {
case HOMEKIT_ENDPOINT_PAIR_SETUP: {
homekit_server_on_pair_setup(context, (const byte *)context->body, context->body_length);
break;
}
case HOMEKIT_ENDPOINT_PAIR_VERIFY: {
homekit_server_on_pair_verify(context, (const byte *)context->body, context->body_length);
break;
}
default: {
DEBUG("Unknown endpoint");
send_404_response(context);
break;
}
}
} else {
switch(context->endpoint) {
case HOMEKIT_ENDPOINT_IDENTIFY: {
homekit_server_on_identify(context);
break;
}
case HOMEKIT_ENDPOINT_GET_ACCESSORIES: {
homekit_server_on_get_accessories(context);
break;
}
case HOMEKIT_ENDPOINT_GET_CHARACTERISTICS: {
homekit_server_on_get_characteristics(context);
break;
}
case HOMEKIT_ENDPOINT_UPDATE_CHARACTERISTICS: {
homekit_server_on_update_characteristics(context, (const byte *)context->body, context->body_length);
break;
}
case HOMEKIT_ENDPOINT_PAIRINGS: {
homekit_server_on_pairings(context, (const byte *)context->body, context->body_length);
break;
}
case HOMEKIT_ENDPOINT_RESOURCE: {
homekit_server_on_resource(context);
break;
}
default: {
DEBUG("Unknown endpoint");
send_404_response(context);
break;
}
}
}

//    if (!context->encrypted) {
        switch(context->endpoint) {
            case HOMEKIT_ENDPOINT_PAIR_SETUP: {
                homekit_server_on_pair_setup(context, (const byte *)context->body, context->body_length);
                break;
            }
            case HOMEKIT_ENDPOINT_PAIR_VERIFY: {
                homekit_server_on_pair_verify(context, (const byte *)context->body, context->body_length);
                break;
            }
//            default: {
//                DEBUG("Unknown endpoint");
//                send_404_response(context);
//                break;
//            }
//        }
//    } else {
//        switch(context->endpoint) {
            case HOMEKIT_ENDPOINT_IDENTIFY: {
                if (context->encrypted || true) {
                    homekit_server_on_identify(context);
                }
                break;
            }
            case HOMEKIT_ENDPOINT_GET_ACCESSORIES: {
                if (context->encrypted || true) {
                    homekit_server_on_get_accessories(context);
                }
                break;
            }
            case HOMEKIT_ENDPOINT_GET_CHARACTERISTICS: {
                if (context->encrypted || true) {
                    homekit_server_on_get_characteristics(context);
                }
                break;
            }
            case HOMEKIT_ENDPOINT_UPDATE_CHARACTERISTICS: {
                if (context->encrypted || true) {
                    homekit_server_on_update_characteristics(context, (const byte *)context->body, context->body_length);
                }
                break;
            }
            case HOMEKIT_ENDPOINT_PAIRINGS: {
                if (context->encrypted || true) {
                    homekit_server_on_pairings(context, (const byte *)context->body, context->body_length);
                }
                break;
            }
            case HOMEKIT_ENDPOINT_RESOURCE: {
                if (context->encrypted || true) {
                    homekit_server_on_resource(context);
                }
                break;
            }
            default: {
                DEBUG("Unknown endpoint");
                send_404_response(context);
                break;
            }
        }
//    }

And unencrypted commands work great.

The 'Feature Request' would be to have the connections encrypted so they conformed to the HomeKit standard. Unfortunately, my skills are limited to commenting code, copy-paste code, and some educated guessing; this feature is so far beyond the realm of my abilities...

I don't think a 'Bridge' is what I need. Right now, esp-homekit is a server only. Really, it would need to implement a client side connection (much like your iPhone) and pair with the remote device to establish the ephemeral shared secret to use for encryption.

This feature request is low priority; unencrypted commands work fine, and I don't need to implement them often; only for 2-way switching, like on a stair case. It'd just be nice to have.

Right now, I plan to save the command as a JSON with host, HTTP method and payload. That way, it can be used with any HTTP API. For sending a payload to another esp-homekit device, the payload is something like;
{"characteristics":[{"aid":1,"iid":9,"value":"ON"},{"aid":1,"iid":9,"value":"BRIGHTNESS"}]}

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants