diff --git a/data/data.go b/data/data.go index 4c2455a..1ebbb10 100644 --- a/data/data.go +++ b/data/data.go @@ -66,24 +66,36 @@ func InsertSets(sets Sets) { m := model.Measurement() q := m.Insert(m.Time, m.MeterID, - m.CGem1, m.CGem2, m.CGem3, + m.CGem1, m.CGem2, m.CGem3, m.CGemN, m.Ep1, m.Ep2, m.Ep3, - m.IGem1, m.IGem2, m.IGem3, + m.IGem1, m.IGem2, m.IGem3, m.IGemN, m.IMax1, m.IMax2, m.IMax3, m.PMax1, m.PMax2, m.PMax3, m.SMax1, m.SMax2, m.SMax3, - m.UGem1, m.UGem2, m.UGem3, + m.UGem1, m.UGem2, m.UGem3, m.UGemN, + m.BGem1, m.BGem2, m.BGem3, m.BGemN, + m.SGem1, m.SGem2, m.SGem3, m.SGemN, + m.PGem1, m.PGem2, m.PGem3, m.PGemN, + m.Ithd1, m.Ithd2, m.Ithd3, m.IthdN, + m.Uthd1, m.Uthd2, m.Uthd3, m.UthdN, + m.Freq, ) for k, v := range sets { q.Values(k.Time, k.Meter, - v[`CGem1`], v[`CGem2`], v[`CGem3`], + v[`CGem1`], v[`CGem2`], v[`CGem3`], ifExists(v, `CGemN`), v[`EP1`], v[`EP2`], v[`EP3`], - v[`IGem1`], v[`IGem2`], v[`IGem3`], + v[`IGem1`], v[`IGem2`], v[`IGem3`], ifExists(v, `IGemN`), v[`IMax1`], v[`IMax2`], v[`IMax3`], v[`PMax1`], v[`PMax2`], v[`PMax3`], v[`SMax1`], v[`SMax2`], v[`SMax3`], - v[`UGem1`], v[`UGem2`], v[`UGem3`], + v[`UGem1`], v[`UGem2`], v[`UGem3`], ifExists(v, `UGemN`), + v[`BGem1`], v[`BGem2`], v[`BGem3`], ifExists(v, `BGemN`), + v[`SGem1`], v[`SGem2`], v[`SGem3`], ifExists(v, `SGemN`), + v[`PGem1`], v[`PGem2`], v[`PGem3`], ifExists(v, `PGemN`), + v[`ITHD1`], v[`ITHD2`], v[`ITHD3`], ifExists(v, `ITHDN`), + v[`UTHD1`], v[`UTHD2`], v[`UTHD3`], ifExists(v, `UTHDN`), + v[`FREQ`], ) } @@ -92,3 +104,12 @@ func InsertSets(sets Sets) { panic(err) } } + +func ifExists(set Set, k string) interface{} { + v, ok := set[k] + if !ok { + return nil + } + + return v +} diff --git a/envitron/receive.go b/envitron/receive.go index a215e3e..627e813 100644 --- a/envitron/receive.go +++ b/envitron/receive.go @@ -46,10 +46,10 @@ func handleReq(c echo.Context) error { } for _, m := range v.Modules { - if m.Port == 4 { - continue - } p := strconv.Itoa(m.Port) + if p == `4` { + p = `N` + } sets[key][`UGem`+p] = m.Voltage sets[key][`IGem`+p] = m.Ampere diff --git a/fortoprt/fetch.go b/fortoprt/fetch.go new file mode 100644 index 0000000..28c7db2 --- /dev/null +++ b/fortoprt/fetch.go @@ -0,0 +1,113 @@ +package fortoprt + +import ( + "encoding/json" + "fmt" + "strconv" + "time" + + "git.fuyu.moe/5GPowerQuality/parser/data" + "git.fuyu.moe/5GPowerQuality/parser/shared" + "golang.org/x/net/websocket" +) + +type message struct { + MessageInfo struct { + Version string + Application string + Module string + Function string + } + Data map[string]measurement +} + +type measurement struct { + DeviceID int + Timestamp shared.UnixTimestamp + Value float64 + Unit string +} + +var host = `dcem5g.ddns.net` + +func FetchData() { + fmt.Println(`Connecting`) + + conn, err := websocket.Dial(`ws://`+host+`/ValuesSocketServer/VMvalues`, ``, `http://localhost`) + if err != nil { + panic(err) + } + defer conn.Close() + + requestData(conn, 1) + requestData(conn, 2) + + for { + b, n := make([]byte, 16384), 0 + + msg := message{} + + for { + nn, err := conn.Read(b[n:]) + if err != nil { + panic(err) + } + n += nn + + err = json.Unmarshal(b[:n], &msg) + if err != nil { + continue + } + + break + } + + // sets := data.Sets{} + mID := data.GetMeterID(data.SourceFortop, host+`-`+strconv.Itoa(msg.Data["U1"].DeviceID)) + + sets := data.Sets{} + for k, v := range msg.Data { + key := data.Key{Meter: mID, Time: time.Time(v.Timestamp)} + if _, ok := sets[key]; !ok { + sets[key] = data.Set{} + } + + if len(k) == 2 { + n := k[1:] + if n == `4` { + n = `N` + } + + k = k[:1] + `Gem` + n + } + + sets[key][k] = v.Value + } + + data.InsertSets(sets) + } +} + +func requestData(conn *websocket.Conn, meter int) { + write(conn, `{"MESSAGEINFO":{"VERSION":1,"APPLICATION":"DCEM_ENTERPRISE","MODULE":"LIVEDATA","FUNCTION":"REQUEST_DATASTREAM","REVISION":1},"VARS":{"DEVICEID":`+strconv.Itoa(meter)+`,"VALUES":`+values+`}}`) +} + +func write(conn *websocket.Conn, msg string) { + _, err := conn.Write([]byte(msg)) + if err != nil { + panic(err) + } +} + +var values = `[ +"U1", "U2", "U3", "U4", +"I1", "I2", "I3", "I4", +"P1", "P2", "P3", "P4", +"B1", "B2", "B3", "B4", +"S1", "S2", "S3", "S4", +"C1", "C2", "C3", "C4", +"EP1", "EP2", "EP3", "EP4", +"UTHD1", "UTHD2", "UTHD3", "UTHD4", +"ITHD1", "ITHD2", "ITHD3", "ITHD4", +"FREQ" +]` diff --git a/internal/migrations/files/0006.sql b/internal/migrations/files/0006.sql new file mode 100644 index 0000000..6583e5a --- /dev/null +++ b/internal/migrations/files/0006.sql @@ -0,0 +1,3 @@ +ALTER TABLE measurement + ADD i_gem_n DOUBLE PRECISION, + ADD u_gem_n DOUBLE PRECISION; diff --git a/internal/migrations/files/0007.sql b/internal/migrations/files/0007.sql new file mode 100644 index 0000000..8ea5ba0 --- /dev/null +++ b/internal/migrations/files/0007.sql @@ -0,0 +1,29 @@ +ALTER TABLE measurement + ADD b_gem_1 DOUBLE PRECISION, + ADD b_gem_2 DOUBLE PRECISION, + ADD b_gem_3 DOUBLE PRECISION, + ADD b_gem_n DOUBLE PRECISION, + + ADD s_gem_1 DOUBLE PRECISION, + ADD s_gem_2 DOUBLE PRECISION, + ADD s_gem_3 DOUBLE PRECISION, + ADD s_gem_n DOUBLE PRECISION, + + ADD p_gem_1 DOUBLE PRECISION, + ADD p_gem_2 DOUBLE PRECISION, + ADD p_gem_3 DOUBLE PRECISION, + ADD p_gem_n DOUBLE PRECISION, + + ADD uthd_1 DOUBLE PRECISION, + ADD uthd_2 DOUBLE PRECISION, + ADD uthd_3 DOUBLE PRECISION, + ADD uthd_n DOUBLE PRECISION, + + ADD ithd_1 DOUBLE PRECISION, + ADD ithd_2 DOUBLE PRECISION, + ADD ithd_3 DOUBLE PRECISION, + ADD ithd_n DOUBLE PRECISION, + + ADD c_gem_n DOUBLE PRECISION, + + ADD freq DOUBLE PRECISION; diff --git a/internal/model/db.json b/internal/model/db.json index 48384f2..7c56175 100644 --- a/internal/model/db.json +++ b/internal/model/db.json @@ -2,6 +2,30 @@ { "name": "public.measurement", "fields": [ + { + "name": "b_gem_1", + "data_type": "double precision", + "null": true, + "size": 8 + }, + { + "name": "b_gem_2", + "data_type": "double precision", + "null": true, + "size": 8 + }, + { + "name": "b_gem_3", + "data_type": "double precision", + "null": true, + "size": 8 + }, + { + "name": "b_gem_n", + "data_type": "double precision", + "null": true, + "size": 8 + }, { "name": "c_gem_1", "data_type": "double precision", @@ -17,6 +41,12 @@ "data_type": "double precision", "size": 8 }, + { + "name": "c_gem_n", + "data_type": "double precision", + "null": true, + "size": 8 + }, { "name": "ep_1", "data_type": "double precision", @@ -32,6 +62,12 @@ "data_type": "double precision", "size": 8 }, + { + "name": "freq", + "data_type": "double precision", + "null": true, + "size": 8 + }, { "name": "i_gem_1", "data_type": "double precision", @@ -47,6 +83,12 @@ "data_type": "double precision", "size": 8 }, + { + "name": "i_gem_n", + "data_type": "double precision", + "null": true, + "size": 8 + }, { "name": "i_max_1", "data_type": "double precision", @@ -62,11 +104,59 @@ "data_type": "double precision", "size": 8 }, + { + "name": "ithd_1", + "data_type": "double precision", + "null": true, + "size": 8 + }, + { + "name": "ithd_2", + "data_type": "double precision", + "null": true, + "size": 8 + }, + { + "name": "ithd_3", + "data_type": "double precision", + "null": true, + "size": 8 + }, + { + "name": "ithd_n", + "data_type": "double precision", + "null": true, + "size": 8 + }, { "name": "meter_id", "data_type": "integer", "size": 4 }, + { + "name": "p_gem_1", + "data_type": "double precision", + "null": true, + "size": 8 + }, + { + "name": "p_gem_2", + "data_type": "double precision", + "null": true, + "size": 8 + }, + { + "name": "p_gem_3", + "data_type": "double precision", + "null": true, + "size": 8 + }, + { + "name": "p_gem_n", + "data_type": "double precision", + "null": true, + "size": 8 + }, { "name": "p_max_1", "data_type": "double precision", @@ -82,6 +172,30 @@ "data_type": "double precision", "size": 8 }, + { + "name": "s_gem_1", + "data_type": "double precision", + "null": true, + "size": 8 + }, + { + "name": "s_gem_2", + "data_type": "double precision", + "null": true, + "size": 8 + }, + { + "name": "s_gem_3", + "data_type": "double precision", + "null": true, + "size": 8 + }, + { + "name": "s_gem_n", + "data_type": "double precision", + "null": true, + "size": 8 + }, { "name": "s_max_1", "data_type": "double precision", @@ -116,6 +230,36 @@ "name": "u_gem_3", "data_type": "double precision", "size": 8 + }, + { + "name": "u_gem_n", + "data_type": "double precision", + "null": true, + "size": 8 + }, + { + "name": "uthd_1", + "data_type": "double precision", + "null": true, + "size": 8 + }, + { + "name": "uthd_2", + "data_type": "double precision", + "null": true, + "size": 8 + }, + { + "name": "uthd_3", + "data_type": "double precision", + "null": true, + "size": 8 + }, + { + "name": "uthd_n", + "data_type": "double precision", + "null": true, + "size": 8 } ] }, diff --git a/main.go b/main.go index 27bc95c..548b9e3 100644 --- a/main.go +++ b/main.go @@ -4,6 +4,7 @@ import ( "git.fuyu.moe/5GPowerQuality/parser/data" "git.fuyu.moe/5GPowerQuality/parser/envitron" "git.fuyu.moe/5GPowerQuality/parser/fortop" + "git.fuyu.moe/5GPowerQuality/parser/fortoprt" "git.fuyu.moe/Fuyu/flog" ) @@ -16,7 +17,8 @@ func main() { data.InitDB() - go fetchFortopData() + // go fetchFortopData() + go fortoprt.FetchData() envitron.ReceiveData() } diff --git a/shared/type.go b/shared/type.go index 9ab8246..534d7fc 100644 --- a/shared/type.go +++ b/shared/type.go @@ -14,7 +14,15 @@ func (t *UnixTimestamp) UnmarshalText(b []byte) error { if err != nil { return err } - *t = UnixTimestamp(time.Unix(i, 0)) + + var tt time.Time + if len(b) > 10 { + tt = time.Unix(0, i) + } else { + tt = time.Unix(i, 0) + } + + *t = UnixTimestamp(tt) return nil }