Skip to content

Commit

Permalink
0.5.0 release candidate (beta 12)
Browse files Browse the repository at this point in the history
  • Loading branch information
raoulvm committed Apr 8, 2023
1 parent 6d08500 commit 2007359
Show file tree
Hide file tree
Showing 7 changed files with 561 additions and 525 deletions.
7 changes: 7 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,12 @@
# Changelog

## 0.5.0
- **BREAKING CHANGES**
The configuration of the KNX gateway (knxd or multicast) has been moved to homebridge's config.json again, to make it configurable using the homebridge UI
- homebridge UI support for creating child bridges
- knx configuration files can now be YAML files (extension must be `.yaml`)
- knx configuration files can now be splitted into multiple files - only one file per child bridge should contain any other contents than `Devices`

## 0.4.3
- merged PR #198 (Update WindowCoveringTilt.js) by @EyeOfTheStorm
- merged PR #204 (Update GarageDoorOpenerAdvanced.js) by @christof-fersch
Expand Down
19 changes: 12 additions & 7 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
# homebridge-knx Version 0.4
# homebridge-knx Version 0.5
[![NPM version][npm-image]][npm-url] [![Downloads][downloads-image]][npm-url][![Dependency status][david-dm-image]][david-dm-url]

KNX platform shim for homebridge.
Expand All @@ -21,10 +21,11 @@ I cannot support the knxd. Please address issues directly at the [knxd issue pag
- Install homebridge first, from [https://homebridge.io/](https://homebridge.io/);
- Once you have your instance running (without any devices yet), go to the `Plugins` tab and type `knx` in the search box
- `homebridge-knx` should be within the top five hits (yes, there are alternatives), please check the name before installing
- Then put the configuration file *knx_config.json* into `~/.homebridge` (or another folder to your liking, but it should be reaadable and writable by user `homebridge` or group `homebridge` which is created by the homebridge installer), and adapt them to your needs (knxd address and some test devices in `knx_config.json`)
- Eliminate everything (especially all group addresses) that might harm your KNX installation. Sending bus telegrams to your alarm device might wake the neighbourhood unpleasantly!
- If you used the dfeault paths (~/.homebridge/knx_config.json) you can just restart homebridge using the GUI
- If you didn't, or want to use child bridges for more accessories (than 149) you need to configure homebridge (using the GUI e.g.). The following sample is from my test installation
- Then put the configuration file *knx_config.json* into `~/.homebridge` (or another folder to your liking, but it should be **readable** and **writable** by user `homebridge` or group `homebridge` which is created by the homebridge installer), and adapt them to your needs (knxd address and some test devices in `knx_config.json`)
- Eliminate everything (especially all group addresses) that might harm your KNX installation. Sending bus telegrams to your alarm device might wake the neighbourhood unpleasantly!
- Use the homebridge UI to create platform instances. You need to specify a name (your choice), a file name or path to th eknx configuration files, and the means of communication with the KNX bus (knxd or KNX multicast).
- You can use the UI to move the platform instances you have created into _child bridges_, which is **heavily encouraged**.
- You can look at (or even modify) the config using the UI. The following sample is from my test installation

```json
{
Expand All @@ -49,15 +50,19 @@ I cannot support the knxd. Please address issues directly at the [knxd issue pag
{
"name": "KNX",
"platform": "KNX",
"config_path": "/home/pi/homebridge/dg-knx_config.json"
"config_path": "/home/pi/homebridge/dg-knx_config.json",
"_bridge": {
"username": "1E:0B:9B:24:17:01",
"port": 51490
}
},
{
"name": "KNX",
"platform": "KNX",
"config_path": "/home/pi/homebridge/og-knx_config.json",
"_bridge": {
"username": "0E:0B:9B:24:17:00",
"port": 51490
"port": 51492
}
}
]
Expand Down
8 changes: 4 additions & 4 deletions index.js
Original file line number Diff line number Diff line change
Expand Up @@ -185,10 +185,10 @@ KNXPlatform.prototype.configure = function () {

/* *************** read the config the first time
*
*/
if (!this.config.GroupAddresses) {
this.config.GroupAddresses = [];
}
// */
// if (!this.config.GroupAddresses) {
// this.config.GroupAddresses = [];
// }

// iterate through all devices the platform my offer
// for each device, create an accessory
Expand Down
206 changes: 103 additions & 103 deletions lib/groupaddress.js
Original file line number Diff line number Diff line change
Expand Up @@ -14,17 +14,17 @@
* @param {boolean} reversed - Indicates if Boolean or Percentage values should be counted down instead of up
*/
function GroupAddress(gaNumber, name, dptype, readable, readOnStartup, writable, comment, reversed) {
this.address = gaNumber;
this.name = name;
this.address = gaNumber;
this.name = name;

//todo: This check requires a string, not an object from the list
this.dptype = (dptype in DPTTypes) ? DPTTypes[dptype] : DPTTypes.DPT1;
//todo: This check requires a string, not an object from the list
this.dptype = (dptype in DPTTypes) ? DPTTypes[dptype] : DPTTypes.DPT1;

this.readable = (readable !== false);
this.readOnStartup = (readOnStartup !== false);
this.writable = (writable !== false);
this.comment = comment;
this.reversed = (reversed == true); // the evil twins are right here.
this.readable = (readable !== false);
this.readOnStartup = (readOnStartup !== false);
this.writable = (writable !== false);
this.comment = comment;
this.reversed = (reversed == true); // the evil twins are right here.
}

// change from 31 to 15: fixes issue #69 https://github.com/snowdd1/homebridge-knx/issues/69
Expand All @@ -38,30 +38,30 @@ function GroupAddress(gaNumber, name, dptype, readable, readOnStartup, writable,
* @param {String} groupAddress - Address as String, such as "15/7/255"
* @returns {String}
*/
var validateAddressText = function(groupAddress) {
if (typeof groupAddress !== 'string') {
return 'ERR Invalid parameter';
}
// assume triple notation (0..31) (0..7) (0..255)
// extended to 5 bit for first triple
// https://github.com/snowdd1/homebridge-knx/issues/72
// https://github.com/andreek/node-eibd/pull/41
var addressArray = groupAddress.match(/^(([0-9]|[1-9][0-9]{1,2})\/([0-9]|[1-9][0-9]{1,2})\/([0-9]|[1-9][0-9]{1,2}))/);
if (!addressArray) {
// no valid structure
return 'ERR no valid group address structure (31/7/255)';
}
// change from 31 to 15: fixes issue #69 https://github.com/snowdd1/homebridge-knx/issues/69
if (parseInt(addressArray[2]) > 31) {
return 'ERR no valid group address structure (31/7/255): first triple exceeds 31';
}
if (parseInt(addressArray[3]) > 7) {
return 'ERR no valid group address structure (31/7/255): second triple exceeds 7';
}
if (parseInt(addressArray[4]) > 255) {
return 'ERR no valid group address structure (31/7/255): third triple exceeds 255';
}
return 'OK';
var validateAddressText = function (groupAddress) {
if (typeof groupAddress !== 'string') {
return 'ERR Invalid parameter';
}
// assume triple notation (0..31) (0..7) (0..255)
// extended to 5 bit for first triple
// https://github.com/snowdd1/homebridge-knx/issues/72
// https://github.com/andreek/node-eibd/pull/41
var addressArray = groupAddress.match(/^(([0-9]|[1-9][0-9]{1,2})\/([0-9]|[1-9][0-9]{1,2})\/([0-9]|[1-9][0-9]{1,2}))/);
if (!addressArray) {
// no valid structure
return 'ERR no valid group address structure (31/7/255)';
}
// change from 31 to 15: fixes issue #69 https://github.com/snowdd1/homebridge-knx/issues/69
if (parseInt(addressArray[2]) > 31) {
return 'ERR no valid group address structure (31/7/255): first triple exceeds 31';
}
if (parseInt(addressArray[3]) > 7) {
return 'ERR no valid group address structure (31/7/255): second triple exceeds 7';
}
if (parseInt(addressArray[4]) > 255) {
return 'ERR no valid group address structure (31/7/255): third triple exceeds 255';
}
return 'OK';
};

/**
Expand All @@ -70,11 +70,11 @@ var validateAddressText = function(groupAddress) {
* @param {String} groupAddress
* @returns {Boolean}
*/
var validateAddress = function(groupAddress) {
if (validateAddressText(groupAddress) === 'OK') {
return true;
}
return false;
var validateAddress = function (groupAddress) {
if (validateAddressText(groupAddress) === 'OK') {
return true;
}
return false;
};


Expand All @@ -84,80 +84,80 @@ var validateAddressText = function(groupAddress) {
* @param {characteristic} characteristic - the characteristic to be bound, for automatic type derivation.
* @returns {GroupAddress}
*/
var gaComplete = function(address, globs, Characteristic){
// look for the address in the global group address list
if (!globs.config.GroupAddresses[address]) {
globs.log("The Group Address " + address + " is not yet defined. Type testing is not supported. Assuming match to HomeKit type");
if (Characteristic.props.format === globs.Characteristic.Formats.BOOL) {
// Boolean
return new GroupAddress(address, 'automatically generated', DPTTypes.DPT1, true, true, true, 'INITIAL')
} else if (Characteristic.props.format === globs.Characteristic.Formats.INT || Characteristic.props.format === globs.Characteristic.Formats.UINT8) {
if (Characteristic.props.unit === globs.Characteristic.Units.PERCENTAGE) {
// percentage
return new GroupAddress(address, 'automatically generated', DPTTypes['DPT5.001'], true, true, true, 'INITIAL');
} else {
// integer (assuming 1 byte)
return new GroupAddress(address, 'automatically generated', DPTTypes.DPT5, true, true, true, 'INITIAL');
}
var gaComplete = function (address, globs, Characteristic) {
// look for the address in the global group address list
//if (!globs.config.GroupAddresses[address]) {
//globs.log("The Group Address " + address + " is not yet defined. Type testing is not supported. Assuming match to HomeKit type");
if (Characteristic.props.format === globs.Characteristic.Formats.BOOL) {
// Boolean
return new GroupAddress(address, 'automatically generated', DPTTypes.DPT1, true, true, true, 'INITIAL')
} else if (Characteristic.props.format === globs.Characteristic.Formats.INT || Characteristic.props.format === globs.Characteristic.Formats.UINT8) {
if (Characteristic.props.unit === globs.Characteristic.Units.PERCENTAGE) {
// percentage
return new GroupAddress(address, 'automatically generated', DPTTypes['DPT5.001'], true, true, true, 'INITIAL');
} else {
// integer (assuming 1 byte)
return new GroupAddress(address, 'automatically generated', DPTTypes.DPT5, true, true, true, 'INITIAL');
}

} else if (Characteristic.props.format === globs.Characteristic.Formats.FLOAT) {
return new GroupAddress(address, 'automatically generated', DPTTypes.DPT9, true, true, true, 'INITIAL')
}
} else {
return new GroupAddress(address, globs.config.GroupAddresses[address].name, globs.config.GroupAddresses[address].dptype,
globs.config.GroupAddresses[address].readable, globs.config.GroupAddresses[address].readOnStartup,
globs.config.GroupAddresses[address].writable, globs.config.GroupAddresses[address].comment);
} else if (Characteristic.props.format === globs.Characteristic.Formats.FLOAT) {
return new GroupAddress(address, 'automatically generated', DPTTypes.DPT9, true, true, true, 'INITIAL')
}
// } else {
// return new GroupAddress(address, globs.config.GroupAddresses[address].name, globs.config.GroupAddresses[address].dptype,
// globs.config.GroupAddresses[address].readable, globs.config.GroupAddresses[address].readOnStartup,
// globs.config.GroupAddresses[address].writable, globs.config.GroupAddresses[address].comment);

}
// }
}

var validDPTTypes = {
DPT1 : "DPT1",
DPT5 : "DPT5",
DPT9 : "DPT9",
DPT1_002 : "DPT1.002",
DPT1_011 : "DPT1.011",
DPT5_001 : "DPT5.001"
DPT1: "DPT1",
DPT5: "DPT5",
DPT9: "DPT9",
DPT1_002: "DPT1.002",
DPT1_011: "DPT1.011",
DPT5_001: "DPT5.001"
};

var DPTTypes = {
DPT1 : {
type : "DPT1",
char : "boolean",
name : "generic 1 bit"
},
DPT5 : {
type : "DPT5",
char : "int",
name : "generic 1 byte unsigned integer"
},
DPT9 : {
type : "DPT9",
char : "float",
name : "generic 2 bytes float"
},
"DPT1.002" : {
type : "DPT1.002",
char : "boolean",
name : "Boolean"
},
"DPT1.011" : {
type : "DPT1.011",
char : "boolean",
name : "Status"
},
"DPT5.001" : {
type : "DPT5.001",
char : "percentage",
name : "Percentage"
}
DPT1: {
type: "DPT1",
char: "boolean",
name: "generic 1 bit"
},
DPT5: {
type: "DPT5",
char: "int",
name: "generic 1 byte unsigned integer"
},
DPT9: {
type: "DPT9",
char: "float",
name: "generic 2 bytes float"
},
"DPT1.002": {
type: "DPT1.002",
char: "boolean",
name: "Boolean"
},
"DPT1.011": {
type: "DPT1.011",
char: "boolean",
name: "Status"
},
"DPT5.001": {
type: "DPT5.001",
char: "percentage",
name: "Percentage"
}
};

module.exports = {
GroupAddress : GroupAddress,
DPTTypes : DPTTypes,
validDPTTypes : validDPTTypes,
gaComplete: gaComplete,
validateAddressText: validateAddressText,
validateAddress: validateAddress
GroupAddress: GroupAddress,
DPTTypes: DPTTypes,
validDPTTypes: validDPTTypes,
gaComplete: gaComplete,
validateAddressText: validateAddressText,
validateAddress: validateAddress
};
Loading

0 comments on commit 2007359

Please sign in to comment.