1
0
Fork 0

Adding upstream version 1.34.4.

Signed-off-by: Daniel Baumann <daniel@debian.org>
This commit is contained in:
Daniel Baumann 2025-05-24 07:26:29 +02:00
parent e393c3af3f
commit 4978089aab
Signed by: daniel
GPG key ID: FBB4F0E80A80222F
4963 changed files with 677545 additions and 0 deletions

View file

@ -0,0 +1,126 @@
# Neoom Beaam Input Plugin
This plugin gathers metrics from a [Neoom Beaam gateway][beaam] using the
[Beaam API][beaam_api] with access token that can be created in the Neoom web
interface. Please follow the [developer instructions][devpage] to create the
token.
⭐ Telegraf v1.33.0
🏷️ iot
💻 all
[beaam]: https://neoom.com/en/products/beaam
[beaam_api]: https://developer.neoom.com/reference/concepts-terms-1
[devpage]:https://neoom.com/developers
## Global configuration options <!-- @/docs/includes/plugin_config.md -->
In addition to the plugin-specific configuration settings, plugins support
additional global and plugin configuration settings. These settings are used to
modify metrics, tags, and field or create aliases and configure ordering, etc.
See the [CONFIGURATION.md][CONFIGURATION.md] for more details.
[CONFIGURATION.md]: ../../../docs/CONFIGURATION.md#plugins
## Secret-store support
This plugin supports secrets from secret-stores for the `token` option.
See the [secret-store documentation][SECRETSTORE] for more details on how
to use them.
[SECRETSTORE]: ../../../docs/CONFIGURATION.md#secret-store-secrets
## Configuration
```toml @sample.conf
# Read energy data from the local Neoom Beaam gateway
[[inputs.neoom_beaam]]
## Address of the gateway
# address = "https://10.10.10.10"
## Bearer token for accessing the data
# token = ""
## Enforce refreshing the site configuration in each gather cycle
# refresh_configuration = false
## Optional TLS Config
## Set to true/false to enforce TLS being enabled/disabled. If not set,
## enable TLS only if any of the other options are specified.
# tls_enable =
## Trusted root certificates for server
# tls_ca = "/path/to/cafile"
## Used for TLS client certificate authentication
# tls_cert = "/path/to/certfile"
## Used for TLS client certificate authentication
# tls_key = "/path/to/keyfile"
## Password for the key file if it is encrypted
# tls_key_pwd = ""
## Send the specified TLS server name via SNI
# tls_server_name = "kubernetes.example.com"
## Minimal TLS version to accept by the client
# tls_min_version = "TLS12"
## List of ciphers to accept, by default all secure ciphers will be accepted
## See https://pkg.go.dev/crypto/tls#pkg-constants for supported values.
## Use "all", "secure" and "insecure" to add all support ciphers, secure
## suites or insecure suites respectively.
# tls_cipher_suites = ["secure"]
## Renegotiation method, "never", "once" or "freely"
# tls_renegotiation_method = "never"
## Use TLS but skip chain & host verification
# insecure_skip_verify = false
```
## Example Output
For energy flow metrics:
```text
neoom_beaam_energy_flow,datapoint=SELF_SUFFICIENCY,source=127.0.0.1,unit=% value=100 1723883145024999936
neoom_beaam_energy_flow,datapoint=POWER_PRODUCTION,source=127.0.0.1,unit=W value=1184 1723883150001999872
neoom_beaam_energy_flow,datapoint=POWER_GRID,source=127.0.0.1,unit=W value=15 1723883150001999872
neoom_beaam_energy_flow,datapoint=POWER_STORAGE,source=127.0.0.1,unit=W value=3504 1723883150001999872
neoom_beaam_energy_flow,datapoint=ENERGY_PRODUCED,source=127.0.0.1,unit=Wh value=639300 1723882905007000064
neoom_beaam_energy_flow,datapoint=ENERGY_IMPORTED,source=127.0.0.1,unit=Wh value=22696.926152777138 1723883150001999872
neoom_beaam_energy_flow,datapoint=ENERGY_EXPORTED,source=127.0.0.1,unit=Wh value=237421.33112499933 1723883135003000064
neoom_beaam_energy_flow,datapoint=ENERGY_CHARGED,source=127.0.0.1,unit=Wh value=215200 1723882765001999872
neoom_beaam_energy_flow,datapoint=ENERGY_DISCHARGED,source=127.0.0.1,unit=Wh value=144800 1723880490004999936
neoom_beaam_energy_flow,datapoint=STATE_OF_CHARGE,source=127.0.0.1,unit=% value=59 1723883090001999872
neoom_beaam_energy_flow,datapoint=POWER_CONSUMPTION_CALC,source=127.0.0.1,unit=W value=4703 1723883150001999872
neoom_beaam_energy_flow,datapoint=ENERGY_CONSUMED_CALC,source=127.0.0.1,unit=Wh value=354175.59502777783 1723883150001999872
```
for thing (aka device) metrics
```text
neoom_beaam_thing,datapoint=CONNECTION,source=127.0.0.1,thing=ELECTRICITY_METER_AC,unit=None value=true 1723890960060000000
neoom_beaam_thing,datapoint=VOLTAGE_P1,source=127.0.0.1,thing=ELECTRICITY_METER_AC,unit=V value=245 1723905135056000000
neoom_beaam_thing,datapoint=VOLTAGE_P2,source=127.0.0.1,thing=ELECTRICITY_METER_AC,unit=V value=242.3 1723905135056000000
neoom_beaam_thing,datapoint=VOLTAGE_P3,source=127.0.0.1,thing=ELECTRICITY_METER_AC,unit=V value=245.5 1723905135056000000
neoom_beaam_thing,datapoint=FREQUENCY,source=127.0.0.1,thing=ELECTRICITY_METER_AC,unit=Hz value=49.98 1723905135056000000
neoom_beaam_thing,datapoint=ACTIVE_POWER,source=127.0.0.1,thing=ELECTRICITY_METER_AC,unit=W value=-826 1723905135056000000
neoom_beaam_thing,datapoint=OUTPUT_ENERGY,source=127.0.0.1,thing=ELECTRICITY_METER_AC,unit=Wh value=241826.44736444377 1723905135075000064
neoom_beaam_thing,datapoint=INPUT_ENERGY,source=127.0.0.1,thing=ELECTRICITY_METER_AC,unit=Wh value=22988.396324999278 1723904090096000000
neoom_beaam_thing,datapoint=POWER_P1,source=127.0.0.1,thing=ELECTRICITY_METER_AC,unit=W value=-305 1723905135056000000
neoom_beaam_thing,datapoint=POWER_P2,source=127.0.0.1,thing=ELECTRICITY_METER_AC,unit=W value=-268 1723905135056000000
neoom_beaam_thing,datapoint=POWER_P3,source=127.0.0.1,thing=ELECTRICITY_METER_AC,unit=W value=-214 1723905135056000000
```
## Metrics
- neoom_beaam_energy_flow
- tags:
- source (address of gateway)
- datapoint (name of the datapoint)
- unit (unit of the measurement)
- fields:
- value (value of the datapoint)
- neoom_beaam_thing
- tags:
- source (address of gateway)
- thing (name of the device)
- datapoint (name of the datapoint)
- unit (unit of the measurement)
- fields:
- value (value of the datapoint)

View file

@ -0,0 +1,310 @@
//go:generate ../../../tools/config_includer/generator
//go:generate ../../../tools/readme_config_includer/generator
package neoom_beaam
import (
"context"
_ "embed"
"encoding/json"
"fmt"
"io"
"net/http"
"net/url"
"strconv"
"strings"
"time"
"github.com/influxdata/telegraf"
"github.com/influxdata/telegraf/config"
"github.com/influxdata/telegraf/internal"
chttp "github.com/influxdata/telegraf/plugins/common/http"
"github.com/influxdata/telegraf/plugins/inputs"
)
//go:embed sample.conf
var sampleConfig string
type NeoomBeaam struct {
Address string `toml:"address"`
Token config.Secret `toml:"token"`
RefreshConfig bool `toml:"refresh_configuration"`
Log telegraf.Logger `toml:"-"`
chttp.HTTPClientConfig
source string
config site
client *http.Client
}
func (*NeoomBeaam) SampleConfig() string {
return sampleConfig
}
func (n *NeoomBeaam) Init() error {
if n.Address == "" {
n.Address = "https://10.10.10.10"
}
n.Address = strings.TrimRight(n.Address, "/")
u, err := url.Parse(n.Address)
if err != nil {
return fmt.Errorf("parsing of address %q failed: %w", n.Address, err)
}
n.source = u.Hostname()
return nil
}
func (n *NeoomBeaam) Start(telegraf.Accumulator) error {
// Create the client
ctx := context.Background()
client, err := n.HTTPClientConfig.CreateClient(ctx, n.Log)
if err != nil {
return fmt.Errorf("creating client failed: %w", err)
}
n.client = client
// Initialize configuration
return n.updateConfiguration()
}
func (n *NeoomBeaam) Gather(acc telegraf.Accumulator) error {
// Refresh the config if requested
if n.RefreshConfig {
if err := n.updateConfiguration(); err != nil {
return err
}
}
// Query the energy flow
if err := n.queryEnergyFlow(acc); err != nil {
acc.AddError(fmt.Errorf("querying site state failed: %w", err))
}
// Query all known things
for _, thing := range n.config.Things {
if err := n.queryThing(acc, thing); err != nil {
acc.AddError(fmt.Errorf("querying thing %q (%s) failed: %w", thing.Name, thing.id, err))
}
}
return nil
}
func (n *NeoomBeaam) Stop() {
if n.client != nil {
n.client.CloseIdleConnections()
}
}
func (n *NeoomBeaam) updateConfiguration() error {
endpoint := n.Address + "/api/v1/site/configuration"
request, err := http.NewRequest("GET", endpoint, nil)
if err != nil {
return fmt.Errorf("creating configuration request failed: %w", err)
}
if !n.Token.Empty() {
token, err := n.Token.Get()
if err != nil {
return fmt.Errorf("getting token failed: %w", err)
}
bearer := "Bearer " + strings.TrimSpace(token.String())
token.Destroy()
request.Header.Set("Authorization", bearer)
}
request.Header.Set("Accept", "application/json")
// Update the configuration
response, err := n.client.Do(request)
if err != nil {
return &internal.StartupError{
Err: fmt.Errorf("querying configuration failed: %w", err),
Retry: true,
}
}
defer response.Body.Close()
body, err := io.ReadAll(response.Body)
if err != nil {
return fmt.Errorf("reading body failed: %w", err)
}
if response.StatusCode != http.StatusOK {
return &internal.StartupError{
Err: fmt.Errorf("configuration query returned %q: %s", response.Status, string(body)),
Retry: 400 <= response.StatusCode && response.StatusCode <= 499,
}
}
if err := json.Unmarshal(body, &n.config); err != nil {
return fmt.Errorf("decoding configuration failed: %w", err)
}
for id, thing := range n.config.Things {
thing.id = id
n.config.Things[id] = thing
}
return nil
}
func (n *NeoomBeaam) queryEnergyFlow(acc telegraf.Accumulator) error {
// Create the request
endpoint := n.Address + "/api/v1/site/state"
request, err := http.NewRequest("GET", endpoint, nil)
if err != nil {
return fmt.Errorf("creating request failed: %w", err)
}
if !n.Token.Empty() {
token, err := n.Token.Get()
if err != nil {
return fmt.Errorf("getting token failed: %w", err)
}
bearer := "Bearer " + strings.TrimSpace(token.String())
token.Destroy()
request.Header.Set("Authorization", bearer)
}
request.Header.Set("Accept", "application/json")
// Execute query
response, err := n.client.Do(request)
if err != nil {
return fmt.Errorf("querying failed: %w", err)
}
defer response.Body.Close()
// Handle response
body, err := io.ReadAll(response.Body)
if err != nil {
return fmt.Errorf("reading body failed: %w", err)
}
if response.StatusCode != http.StatusOK {
return fmt.Errorf("query returned %q: %s", response.Status, string(body))
}
// Decode the data and create metric
var data siteState
if err := json.Unmarshal(body, &data); err != nil {
return fmt.Errorf("decoding failed: %w", err)
}
for _, s := range data.EnergyFlow.States {
if s.Value == nil {
n.Log.Debugf("omitting data point %q (%s) due to 'null' value", s.Key, s.DataPointID)
continue
}
dp, ok := n.config.EnergyFlow.DataPoints[s.DataPointID]
if !ok {
n.Log.Errorf("no data point definition for ID %q", s.DataPointID)
continue
}
tags := map[string]string{
"source": n.source,
"datapoint": s.Key,
"unit": dp.Unit,
}
fields := map[string]interface{}{
"value": s.Value,
}
ts := time.Unix(0, int64(s.Timestamp*float64(time.Millisecond)))
acc.AddFields("neoom_beaam_energy_flow", fields, tags, ts)
}
return nil
}
func (n *NeoomBeaam) queryThing(acc telegraf.Accumulator, thing thingDefinition) error {
// Create the request
endpoint := n.Address + "/api/v1/things/" + thing.id + "/states"
request, err := http.NewRequest("GET", endpoint, nil)
if err != nil {
return fmt.Errorf("creating request failed: %w", err)
}
if !n.Token.Empty() {
token, err := n.Token.Get()
if err != nil {
return fmt.Errorf("getting token failed: %w", err)
}
bearer := "Bearer " + strings.TrimSpace(token.String())
token.Destroy()
request.Header.Set("Authorization", bearer)
}
request.Header.Set("Accept", "application/json")
// Execute query
response, err := n.client.Do(request)
if err != nil {
return fmt.Errorf("querying failed: %w", err)
}
defer response.Body.Close()
// Handle response
body, err := io.ReadAll(response.Body)
if err != nil {
return fmt.Errorf("reading body failed: %w", err)
}
if response.StatusCode != http.StatusOK {
return fmt.Errorf("query returned %q: %s", response.Status, string(body))
}
// Decode the data and create metric
var data thingState
if err := json.Unmarshal(body, &data); err != nil {
return fmt.Errorf("decoding failed: %w", err)
}
for _, s := range data.States {
if s.Value == nil {
n.Log.Debugf("omitting data point %q (%s) due to 'null' value", s.Key, s.DataPointID)
continue
}
dp, ok := thing.DataPoints[s.DataPointID]
if !ok {
n.Log.Errorf("no data point definition for ID %q", s.DataPointID)
continue
}
tags := map[string]string{
"source": n.source,
"thing": thing.Name,
"datapoint": s.Key,
"unit": dp.Unit,
}
var fields map[string]interface{}
if elements, ok := s.Value.([]interface{}); ok {
fields = make(map[string]interface{}, len(elements))
for i, v := range elements {
fields["value_"+strconv.Itoa(i)] = v
}
} else {
fields = map[string]interface{}{
"value": s.Value,
}
}
ts := time.Unix(0, int64(s.Timestamp*float64(time.Millisecond)))
acc.AddFields("neoom_beaam_thing", fields, tags, ts)
}
return nil
}
// Register the plugin
func init() {
inputs.Add("neoom_beaam", func() telegraf.Input {
return &NeoomBeaam{
HTTPClientConfig: chttp.HTTPClientConfig{
Timeout: config.Duration(5 * time.Second),
ResponseHeaderTimeout: config.Duration(5 * time.Second),
},
}
})
}

View file

@ -0,0 +1,115 @@
package neoom_beaam
import (
"net/http"
"net/http/httptest"
"os"
"path/filepath"
"sort"
"strings"
"testing"
"github.com/stretchr/testify/require"
"github.com/influxdata/telegraf"
"github.com/influxdata/telegraf/config"
"github.com/influxdata/telegraf/plugins/inputs"
"github.com/influxdata/telegraf/plugins/parsers/influx"
"github.com/influxdata/telegraf/testutil"
)
func TestCases(t *testing.T) {
// Get all directories in testdata
folders, err := os.ReadDir("testcases")
require.NoError(t, err)
// Register the plugin
inputs.Add("neoom_beaam", func() telegraf.Input {
return &NeoomBeaam{}
})
// Prepare the influx parser for expectations
parser := &influx.Parser{}
require.NoError(t, parser.Init())
for _, f := range folders {
// Only handle folders
if !f.IsDir() {
continue
}
testcasePath := filepath.Join("testcases", f.Name())
configFilename := filepath.Join(testcasePath, "telegraf.conf")
inputFiles := filepath.Join(testcasePath, "*.json")
expectedFilename := filepath.Join(testcasePath, "expected.out")
expectedErrorFilename := filepath.Join(testcasePath, "expected.err")
t.Run(f.Name(), func(t *testing.T) {
// Read the input data
matches, err := filepath.Glob(inputFiles)
require.NoError(t, err)
require.NotEmpty(t, matches)
sort.Strings(matches)
endpoints := make(map[string][]byte, len(matches))
for _, fn := range matches {
buf, err := os.ReadFile(fn)
require.NoError(t, err)
key := strings.TrimSuffix(filepath.Base(fn), filepath.Ext(fn))
if strings.HasPrefix(key, "thing_") {
endpoints["/api/v1/things/"+strings.TrimPrefix(key, "thing_")+"/states"] = buf
} else {
endpoints["/api/v1/site/"+key] = buf
}
}
// Read the expected output if any
var expected []telegraf.Metric
if _, err := os.Stat(expectedFilename); err == nil {
var err error
expected, err = testutil.ParseMetricsFromFile(expectedFilename, parser)
require.NoError(t, err)
}
// Read the expected output if any
var expectedErrors []string
if _, err := os.Stat(expectedErrorFilename); err == nil {
var err error
expectedErrors, err = testutil.ParseLinesFromFile(expectedErrorFilename)
require.NoError(t, err)
require.NotEmpty(t, expectedErrors)
}
// Create a fake API server
server := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
if msg, ok := endpoints[r.URL.Path]; ok {
if _, err := w.Write(msg); err != nil {
w.WriteHeader(http.StatusInternalServerError)
}
} else {
w.WriteHeader(http.StatusNotFound)
}
}))
defer server.Close()
// Load the configuration
cfg := config.NewConfig()
require.NoError(t, cfg.LoadConfig(configFilename))
require.Len(t, cfg.Inputs, 1)
// Setup and start the plugin
plugin := cfg.Inputs[0].Input.(*NeoomBeaam)
plugin.Address = server.URL
require.NoError(t, plugin.Init())
require.NoError(t, plugin.Start(nil))
defer plugin.Stop()
// Gather the data
var acc testutil.Accumulator
require.NoError(t, plugin.Gather(&acc))
require.Empty(t, acc.Errors)
// Check the metric nevertheless as we might get some metrics despite errors.
actual := acc.GetTelegrafMetrics()
testutil.RequireMetricsEqual(t, expected, actual, testutil.SortMetrics())
})
}
}

View file

@ -0,0 +1,36 @@
# Read energy data from the local Neoom Beaam gateway
[[inputs.neoom_beaam]]
## Address of the gateway
# address = "https://10.10.10.10"
## Bearer token for accessing the data
# token = ""
## Enforce refreshing the site configuration in each gather cycle
# refresh_configuration = false
## Optional TLS Config
## Set to true/false to enforce TLS being enabled/disabled. If not set,
## enable TLS only if any of the other options are specified.
# tls_enable =
## Trusted root certificates for server
# tls_ca = "/path/to/cafile"
## Used for TLS client certificate authentication
# tls_cert = "/path/to/certfile"
## Used for TLS client certificate authentication
# tls_key = "/path/to/keyfile"
## Password for the key file if it is encrypted
# tls_key_pwd = ""
## Send the specified TLS server name via SNI
# tls_server_name = "kubernetes.example.com"
## Minimal TLS version to accept by the client
# tls_min_version = "TLS12"
## List of ciphers to accept, by default all secure ciphers will be accepted
## See https://pkg.go.dev/crypto/tls#pkg-constants for supported values.
## Use "all", "secure" and "insecure" to add all support ciphers, secure
## suites or insecure suites respectively.
# tls_cipher_suites = ["secure"]
## Renegotiation method, "never", "once" or "freely"
# tls_renegotiation_method = "never"
## Use TLS but skip chain & host verification
# insecure_skip_verify = false

View file

@ -0,0 +1,13 @@
# Read energy data from the local Neoom Beaam gateway
[[inputs.neoom_beaam]]
## Address of the gateway
# address = "https://10.10.10.10"
## Bearer token for accessing the data
# token = ""
## Enforce refreshing the site configuration in each gather cycle
# refresh_configuration = false
## Optional TLS Config
{{template "/plugins/common/tls/client.conf"}}

View file

@ -0,0 +1,333 @@
{
"siteId": "11111111-aaaa-1111-aaaa-222222222222",
"versionTimestamp": 1721051934,
"siteInfo": {
"gridConnections": {},
"geoCoordinates": {
"latitude": 48.488256,
"longitude": 14.4954532
}
},
"things": {
"22222222-bbbb-2222-bbbb-222222222222": {
"type": "INVERTER",
"dataPoints": {
"f788ab8b-96d0-5efb-bda7-5214a92418f1": {
"key": "CONNECTION",
"dataType": "BOOLEAN",
"unitOfMeasure": "None"
},
"3d2cf2d0-9c79-583b-b915-f980d0c64817": {
"key": "GRID_FEED_IN_LIMIT",
"dataType": "NUMBER",
"unitOfMeasure": "W"
},
"fb898be0-82f0-5a04-a6f4-e303754cb00c": {
"key": "MAX_POWER_GENERATION_AC",
"dataType": "NUMBER",
"unitOfMeasure": "W"
},
"c0aecdd7-e7f2-52ac-a972-35909c1ac938": {
"key": "STATE_CODE",
"dataType": "STRING",
"unitOfMeasure": "None"
},
"a8aa1122-af0b-5239-9236-73a61d435687": {
"key": "ACTIVE_POWER",
"dataType": "NUMBER",
"unitOfMeasure": "W"
},
"15353bf6-cff1-5182-b299-22cc20762b29": {
"key": "REACTIVE_POWER",
"dataType": "NUMBER",
"unitOfMeasure": "VAr"
},
"ade3343d-333e-58e5-94d6-14d54d44620d": {
"key": "INPUTS_POWER",
"dataType": "NUMBER_ARRAY[]",
"unitOfMeasure": "W"
},
"15de38ea-2c10-5f64-a991-3a3f011c6c23": {
"key": "PRODUCED_ENERGY",
"dataType": "NUMBER",
"unitOfMeasure": "Wh"
}
}
},
"33333333-cccc-3333-cccc-333333333333": {
"type": "BATTERY",
"dataPoints": {
"7748ed36-8535-530c-bf4d-de0f300a8adb": {
"key": "CONNECTION",
"dataType": "BOOLEAN",
"unitOfMeasure": "None"
},
"b4d3ceeb-71f9-5677-ba4f-ac368b8dbd3b": {
"key": "EPS_MODE_ACTIVE",
"dataType": "BOOLEAN",
"unitOfMeasure": "None"
},
"f968a39d-b988-523c-a6d7-ccd1436bfb77": {
"key": "MAX_CURRENT_CHARGE",
"dataType": "NUMBER",
"unitOfMeasure": "A"
},
"d51f9cea-4ed0-556d-ba7c-e8f82ceaf7d0": {
"key": "MAX_CURRENT_DISCHARGE",
"dataType": "NUMBER",
"unitOfMeasure": "A"
},
"5e0188c0-0d26-5158-b837-536a1d8c715f": {
"key": "OPERATING_MODE",
"dataType": "STRING",
"unitOfMeasure": "None"
},
"9df68d84-f679-528c-ad41-4e041d46b6f8": {
"key": "OPERATING_MODES",
"dataType": "STRING_ARRAY[]",
"unitOfMeasure": "None"
},
"8eeb33e5-5c2e-59fa-9d91-c9d12dc833f4": {
"key": "MIN_SOC_SELF_CONSUMPTION_OPT",
"dataType": "NUMBER",
"unitOfMeasure": "%"
},
"f2ea90d0-ca70-5b2d-a5fe-7a62b180e987": {
"key": "MIN_SOC",
"dataType": "NUMBER",
"unitOfMeasure": "%"
},
"d7917007-a8cd-5d8e-8e92-f80237406aad": {
"key": "TARGET_POWER",
"dataType": "NUMBER",
"unitOfMeasure": "W"
},
"94c7f11d-2489-5973-8eaf-57de93426d1b": {
"key": "VOLTAGE",
"dataType": "NUMBER",
"unitOfMeasure": "V"
},
"932f9b7f-4e10-5506-a73a-e8679c3e699f": {
"key": "CURRENT",
"dataType": "NUMBER",
"unitOfMeasure": "A"
},
"9c64cb00-b204-5f1a-8a58-a10d4343fb12": {
"key": "POWER",
"dataType": "NUMBER",
"unitOfMeasure": "W"
},
"a8725a08-f4b5-5cd3-b54f-bd1a879754c9": {
"key": "CELL_TEMPERATURE",
"dataType": "NUMBER",
"unitOfMeasure": "°C"
},
"61740954-99e3-5bd2-a530-c0aa59501d2b": {
"key": "STATE_OF_CHARGE",
"dataType": "NUMBER",
"unitOfMeasure": "%"
},
"899099f9-6ebe-5040-93a6-de0db44f19fb": {
"key": "ERROR_CODES",
"dataType": "STRING_ARRAY[]",
"unitOfMeasure": "None"
},
"6187ec40-ba60-5ec4-9e8a-a4daf5288124": {
"key": "CHARGED_ENERGY",
"dataType": "NUMBER",
"unitOfMeasure": "Wh"
},
"1e1b3efa-f957-51b6-8d35-2de5d682f554": {
"key": "DISCHARGED_ENERGY",
"dataType": "NUMBER",
"unitOfMeasure": "Wh"
},
"a82404ae-a4a5-5a08-86ba-c487dcad55ef": {
"key": "MAX_POWER_CHARGE",
"dataType": "NUMBER",
"unitOfMeasure": "W"
},
"59821d14-13c8-5363-87c1-508095feb2b7": {
"key": "MAX_POWER_DISCHARGE",
"dataType": "NUMBER",
"unitOfMeasure": "W"
},
"f57323b8-4874-58a6-91f9-a9f7c5568a67": {
"key": "DESIRED_SOC",
"dataType": "NUMBER",
"unitOfMeasure": "%"
}
}
},
"44444444-dddd-4444-dddd-444444444444": {
"type": "PV",
"dataPoints": {
"244fa23e-cdbc-5d7d-a3e9-788af3ab43d2": {
"key": "CONNECTIONS",
"dataType": "BOOLEAN_ARRAY[]",
"unitOfMeasure": "None"
},
"d064a7fc-4b9a-5cf4-a55f-eeda5289afac": {
"key": "POWER",
"dataType": "NUMBER",
"unitOfMeasure": "W"
},
"44763dab-6224-5b2a-aadf-d5afd781cdd5": {
"key": "PRODUCED_ENERGY",
"dataType": "NUMBER",
"unitOfMeasure": "Wh"
},
"892e0390-252d-5fb5-9857-04924f1770e1": {
"key": "VOLTAGES",
"dataType": "NUMBER_ARRAY[]",
"unitOfMeasure": "V"
},
"a153ab79-3cf2-5f17-ab40-9af3c38d7e60": {
"key": "CURRENTS",
"dataType": "NUMBER_ARRAY[]",
"unitOfMeasure": "A"
}
}
},
"55555555-eeee-5555-eeee-555555555555": {
"type": "ELECTRICITY_METER_AC",
"dataPoints": {
"094a8ac0-914f-5f0d-a376-d2e3abfdc75e": {
"key": "CONNECTION",
"dataType": "BOOLEAN",
"unitOfMeasure": "None"
},
"22911bdc-0b2f-5008-9d42-c551d4fa53c7": {
"key": "VOLTAGE_P1",
"dataType": "NUMBER",
"unitOfMeasure": "V"
},
"4e34e4eb-0859-5253-81ae-9d536e75c003": {
"key": "VOLTAGE_P2",
"dataType": "NUMBER",
"unitOfMeasure": "V"
},
"a45c0fe9-42e8-5091-9007-ff73d55a149b": {
"key": "VOLTAGE_P3",
"dataType": "NUMBER",
"unitOfMeasure": "V"
},
"755e91d4-f6c6-5570-a2bf-623b20055816": {
"key": "FREQUENCY",
"dataType": "NUMBER",
"unitOfMeasure": "Hz"
},
"c7b812ba-e08b-5f4a-bcd4-97616c8130bc": {
"key": "ACTIVE_POWER",
"dataType": "NUMBER",
"unitOfMeasure": "W"
},
"3f4105ab-bdf8-5d0b-88ba-9859dcf3f111": {
"key": "OUTPUT_ENERGY",
"dataType": "NUMBER",
"unitOfMeasure": "Wh"
},
"6ddbb838-0557-5df0-bdeb-489f426248fb": {
"key": "INPUT_ENERGY",
"dataType": "NUMBER",
"unitOfMeasure": "Wh"
},
"b89fda1c-f19a-5da0-bcbd-4277eb377b3a": {
"key": "POWER_P1",
"dataType": "NUMBER",
"unitOfMeasure": "W"
},
"64fd2faa-13ca-5cc4-8302-3085f13775c8": {
"key": "POWER_P2",
"dataType": "NUMBER",
"unitOfMeasure": "W"
},
"eca4dacc-1858-50f1-ac46-30cddcde75a2": {
"key": "POWER_P3",
"dataType": "NUMBER",
"unitOfMeasure": "W"
}
}
}
},
"energyFlow": {
"dataPoints": {
"27291fe9-b44a-5530-92cf-1fad478f6f66": {
"key": "SELF_SUFFICIENCY",
"dataType": "NUMBER",
"unitOfMeasure": "%"
},
"211f490a-af77-5c33-af3f-fd2e67e40b3f": {
"key": "POWER_PRODUCTION",
"dataType": "NUMBER",
"unitOfMeasure": "W"
},
"58d84d20-ba7c-5218-9045-459e4a946080": {
"key": "POWER_CONSUMPTION",
"dataType": "NUMBER",
"unitOfMeasure": "W"
},
"2548caa8-0288-559c-9e75-50b964f4bf01": {
"key": "POWER_GRID",
"dataType": "NUMBER",
"unitOfMeasure": "W"
},
"b9399b12-e3bb-5515-9b1a-640bd51c1c1b": {
"key": "POWER_STORAGE",
"dataType": "NUMBER",
"unitOfMeasure": "W"
},
"49764da7-5486-52bf-9867-66643445d7fb": {
"key": "ENERGY_PRODUCED",
"dataType": "NUMBER",
"unitOfMeasure": "Wh"
},
"eb0f0b1f-73cc-5cb8-864d-baa11b8628c4": {
"key": "ENERGY_CONSUMED",
"dataType": "NUMBER",
"unitOfMeasure": "Wh"
},
"3dd29b23-eb88-538a-8220-ccd7192d4fef": {
"key": "ENERGY_IMPORTED",
"dataType": "NUMBER",
"unitOfMeasure": "Wh"
},
"804a496b-267b-5783-850d-b43ecc1b6f9c": {
"key": "ENERGY_EXPORTED",
"dataType": "NUMBER",
"unitOfMeasure": "Wh"
},
"25aac409-c380-575f-8429-6a33de6bec3e": {
"key": "ENERGY_CHARGED",
"dataType": "NUMBER",
"unitOfMeasure": "Wh"
},
"42aebe59-8b2c-58fa-a222-991e88451376": {
"key": "ENERGY_DISCHARGED",
"dataType": "NUMBER",
"unitOfMeasure": "Wh"
},
"d40db932-df55-57c9-955b-2528a4df4d73": {
"key": "STATE_OF_CHARGE",
"dataType": "NUMBER",
"unitOfMeasure": "%"
},
"6a7fe53b-65c1-576b-8159-bd79d1fd7651": {
"key": "POWER_CONSUMPTION_CALC",
"dataType": "NUMBER",
"unitOfMeasure": "W"
},
"adf97bab-6a8f-543a-8dab-a7459cc977e7": {
"key": "POWER_GRID_REMAINING",
"dataType": "NUMBER",
"unitOfMeasure": "W"
},
"df4668c6-6d3f-5837-a7c7-e7aaa408f068": {
"key": "ENERGY_CONSUMED_CALC",
"dataType": "NUMBER",
"unitOfMeasure": "Wh"
}
}
},
"externalPlantControls": {}
}

View file

@ -0,0 +1,28 @@
neoom_beaam_energy_flow,datapoint=SELF_SUFFICIENCY,source=127.0.0.1,unit=% value=100 1723883145024999936
neoom_beaam_energy_flow,datapoint=POWER_PRODUCTION,source=127.0.0.1,unit=W value=1184 1723883150001999872
neoom_beaam_energy_flow,datapoint=POWER_GRID,source=127.0.0.1,unit=W value=15 1723883150001999872
neoom_beaam_energy_flow,datapoint=POWER_STORAGE,source=127.0.0.1,unit=W value=3504 1723883150001999872
neoom_beaam_energy_flow,datapoint=ENERGY_PRODUCED,source=127.0.0.1,unit=Wh value=639300 1723882905007000064
neoom_beaam_energy_flow,datapoint=ENERGY_IMPORTED,source=127.0.0.1,unit=Wh value=22696.926152777138 1723883150001999872
neoom_beaam_energy_flow,datapoint=ENERGY_EXPORTED,source=127.0.0.1,unit=Wh value=237421.33112499933 1723883135003000064
neoom_beaam_energy_flow,datapoint=ENERGY_CHARGED,source=127.0.0.1,unit=Wh value=215200 1723882765001999872
neoom_beaam_energy_flow,datapoint=ENERGY_DISCHARGED,source=127.0.0.1,unit=Wh value=144800 1723880490004999936
neoom_beaam_energy_flow,datapoint=STATE_OF_CHARGE,source=127.0.0.1,unit=% value=59 1723883090001999872
neoom_beaam_energy_flow,datapoint=POWER_CONSUMPTION_CALC,source=127.0.0.1,unit=W value=4703 1723883150001999872
neoom_beaam_energy_flow,datapoint=ENERGY_CONSUMED_CALC,source=127.0.0.1,unit=Wh value=354175.59502777783 1723883150001999872
neoom_beaam_thing,datapoint=CONNECTION,source=127.0.0.1,thing=ELECTRICITY_METER_AC,unit=None value=true 1723890960060000000
neoom_beaam_thing,datapoint=VOLTAGE_P1,source=127.0.0.1,thing=ELECTRICITY_METER_AC,unit=V value=245 1723905135056000000
neoom_beaam_thing,datapoint=VOLTAGE_P2,source=127.0.0.1,thing=ELECTRICITY_METER_AC,unit=V value=242.3 1723905135056000000
neoom_beaam_thing,datapoint=VOLTAGE_P3,source=127.0.0.1,thing=ELECTRICITY_METER_AC,unit=V value=245.5 1723905135056000000
neoom_beaam_thing,datapoint=FREQUENCY,source=127.0.0.1,thing=ELECTRICITY_METER_AC,unit=Hz value=49.98 1723905135056000000
neoom_beaam_thing,datapoint=ACTIVE_POWER,source=127.0.0.1,thing=ELECTRICITY_METER_AC,unit=W value=-826 1723905135056000000
neoom_beaam_thing,datapoint=OUTPUT_ENERGY,source=127.0.0.1,thing=ELECTRICITY_METER_AC,unit=Wh value=241826.44736444377 1723905135075000064
neoom_beaam_thing,datapoint=INPUT_ENERGY,source=127.0.0.1,thing=ELECTRICITY_METER_AC,unit=Wh value=22988.396324999278 1723904090096000000
neoom_beaam_thing,datapoint=POWER_P1,source=127.0.0.1,thing=ELECTRICITY_METER_AC,unit=W value=-305 1723905135056000000
neoom_beaam_thing,datapoint=POWER_P2,source=127.0.0.1,thing=ELECTRICITY_METER_AC,unit=W value=-268 1723905135056000000
neoom_beaam_thing,datapoint=POWER_P3,source=127.0.0.1,thing=ELECTRICITY_METER_AC,unit=W value=-214 1723905135056000000
neoom_beaam_thing,datapoint=CONNECTIONS,source=127.0.0.1,thing=PV,unit=None value_0=true,value_1=true 1723890960060000000
neoom_beaam_thing,datapoint=POWER,source=127.0.0.1,thing=PV,unit=W value=245 1723890960060000000
neoom_beaam_thing,datapoint=PRODUCED_ENERGY,source=127.0.0.1,thing=PV,unit=Wh value=335423.1124235639 1723890960060000000
neoom_beaam_thing,datapoint=VOLTAGES,source=127.0.0.1,thing=PV,unit=V value_0=231.42,value_1=302.25 1723890960060000000
neoom_beaam_thing,datapoint=CURRENTS,source=127.0.0.1,thing=PV,unit=A value_0=10.889292196,value_1=69.4789081886 1723890960060000000

View file

@ -0,0 +1,96 @@
{
"energyFlow": {
"states": [
{
"dataPointId": "27291fe9-b44a-5530-92cf-1fad478f6f66",
"key": "SELF_SUFFICIENCY",
"value": 100,
"ts": 1723883145025
},
{
"dataPointId": "211f490a-af77-5c33-af3f-fd2e67e40b3f",
"key": "POWER_PRODUCTION",
"value": 1184,
"ts": 1723883150002
},
{
"dataPointId": "58d84d20-ba7c-5218-9045-459e4a946080",
"key": "POWER_CONSUMPTION",
"value": null,
"ts": 1723877138187
},
{
"dataPointId": "2548caa8-0288-559c-9e75-50b964f4bf01",
"key": "POWER_GRID",
"value": 15,
"ts": 1723883150002
},
{
"dataPointId": "b9399b12-e3bb-5515-9b1a-640bd51c1c1b",
"key": "POWER_STORAGE",
"value": 3504,
"ts": 1723883150002
},
{
"dataPointId": "49764da7-5486-52bf-9867-66643445d7fb",
"key": "ENERGY_PRODUCED",
"value": 639300,
"ts": 1723882905007
},
{
"dataPointId": "eb0f0b1f-73cc-5cb8-864d-baa11b8628c4",
"key": "ENERGY_CONSUMED",
"value": null,
"ts": 1723877138187
},
{
"dataPointId": "3dd29b23-eb88-538a-8220-ccd7192d4fef",
"key": "ENERGY_IMPORTED",
"value": 22696.926152777138,
"ts": 1723883150002
},
{
"dataPointId": "804a496b-267b-5783-850d-b43ecc1b6f9c",
"key": "ENERGY_EXPORTED",
"value": 237421.33112499933,
"ts": 1723883135003
},
{
"dataPointId": "25aac409-c380-575f-8429-6a33de6bec3e",
"key": "ENERGY_CHARGED",
"value": 215200,
"ts": 1723882765002
},
{
"dataPointId": "42aebe59-8b2c-58fa-a222-991e88451376",
"key": "ENERGY_DISCHARGED",
"value": 144800,
"ts": 1723880490005
},
{
"dataPointId": "d40db932-df55-57c9-955b-2528a4df4d73",
"key": "STATE_OF_CHARGE",
"value": 59,
"ts": 1723883090002
},
{
"dataPointId": "6a7fe53b-65c1-576b-8159-bd79d1fd7651",
"key": "POWER_CONSUMPTION_CALC",
"value": 4703,
"ts": 1723883150002
},
{
"dataPointId": "adf97bab-6a8f-543a-8dab-a7459cc977e7",
"key": "POWER_GRID_REMAINING",
"value": null,
"ts": 1723877138187
},
{
"dataPointId": "df4668c6-6d3f-5837-a7c7-e7aaa408f068",
"key": "ENERGY_CONSUMED_CALC",
"value": 354175.59502777783,
"ts": 1723883150002
}
]
}
}

View file

@ -0,0 +1,2 @@
[[inputs.neoom_beaam]]
address = "dummy"

View file

@ -0,0 +1,35 @@
{
"thingId": "44444444-dddd-4444-dddd-444444444444",
"states": [
{
"dataPointId": "244fa23e-cdbc-5d7d-a3e9-788af3ab43d2",
"key": "CONNECTIONS",
"value": [true, true],
"ts": 1723890960060
},
{
"dataPointId": "d064a7fc-4b9a-5cf4-a55f-eeda5289afac",
"key": "POWER",
"value": 245,
"ts": 1723890960060
},
{
"dataPointId": "44763dab-6224-5b2a-aadf-d5afd781cdd5",
"key": "PRODUCED_ENERGY",
"value": 335423.11242356391,
"ts": 1723890960060
},
{
"dataPointId": "892e0390-252d-5fb5-9857-04924f1770e1",
"key": "VOLTAGES",
"value": [231.42, 302.25],
"ts": 1723890960060
},
{
"dataPointId": "a153ab79-3cf2-5f17-ab40-9af3c38d7e60",
"key": "CURRENTS",
"value": [10.889292196, 69.4789081886],
"ts": 1723890960060
}
]
}

View file

@ -0,0 +1,71 @@
{
"thingId": "55555555-eeee-5555-eeee-555555555555",
"states": [
{
"dataPointId": "094a8ac0-914f-5f0d-a376-d2e3abfdc75e",
"key": "CONNECTION",
"value": true,
"ts": 1723890960060
},
{
"dataPointId": "22911bdc-0b2f-5008-9d42-c551d4fa53c7",
"key": "VOLTAGE_P1",
"value": 245,
"ts": 1723905135056
},
{
"dataPointId": "4e34e4eb-0859-5253-81ae-9d536e75c003",
"key": "VOLTAGE_P2",
"value": 242.3,
"ts": 1723905135056
},
{
"dataPointId": "a45c0fe9-42e8-5091-9007-ff73d55a149b",
"key": "VOLTAGE_P3",
"value": 245.5,
"ts": 1723905135056
},
{
"dataPointId": "755e91d4-f6c6-5570-a2bf-623b20055816",
"key": "FREQUENCY",
"value": 49.98,
"ts": 1723905135056
},
{
"dataPointId": "c7b812ba-e08b-5f4a-bcd4-97616c8130bc",
"key": "ACTIVE_POWER",
"value": -826,
"ts": 1723905135056
},
{
"dataPointId": "3f4105ab-bdf8-5d0b-88ba-9859dcf3f111",
"key": "OUTPUT_ENERGY",
"value": 241826.44736444377,
"ts": 1723905135075
},
{
"dataPointId": "6ddbb838-0557-5df0-bdeb-489f426248fb",
"key": "INPUT_ENERGY",
"value": 22988.396324999278,
"ts": 1723904090096
},
{
"dataPointId": "b89fda1c-f19a-5da0-bcbd-4277eb377b3a",
"key": "POWER_P1",
"value": -305,
"ts": 1723905135056
},
{
"dataPointId": "64fd2faa-13ca-5cc4-8302-3085f13775c8",
"key": "POWER_P2",
"value": -268,
"ts": 1723905135056
},
{
"dataPointId": "eca4dacc-1858-50f1-ac46-30cddcde75a2",
"key": "POWER_P3",
"value": -214,
"ts": 1723905135056
}
]
}

View file

@ -0,0 +1,38 @@
package neoom_beaam
type site struct {
EnergyFlow struct {
DataPoints map[string]datapoint `json:"dataPoints"`
} `json:"energyFlow"`
Things map[string]thingDefinition `json:"things"`
}
type siteState struct {
EnergyFlow struct {
States []state `json:"states"`
} `json:"energyFlow"`
}
type thingDefinition struct {
id string
Name string `json:"type"`
DataPoints map[string]datapoint `json:"dataPoints"`
}
type thingState struct {
ID string `json:"thingId"`
States []state `json:"states"`
}
type datapoint struct {
Key string `json:"key"`
DataType string `json:"dataType"`
Unit string `json:"unitOfMeasure"`
}
type state struct {
Key string `json:"key"`
Value interface{} `json:"value"`
DataPointID string `json:"dataPointId"`
Timestamp float64 `json:"ts"`
}