V0.6.5 Arroyo Toad

This commit is contained in:
Christian Risi 2024-12-16 09:57:56 +00:00
parent c47eea3826
commit d0d7799d62
16 changed files with 754 additions and 7 deletions

View File

@ -1,2 +1,6 @@
DB_PASSWORD=abcdefg1234
DB_USER=Admin
DB_PASSWORD=abcd1234
DB_USER=Admin
DB_HOST=iot-data-db.internal
DB=SAPD
DB_PORT=5432
PUBLIC_KEY_DB_URL=http://public-key-db.internal/key

2
.npmrc Normal file
View File

@ -0,0 +1,2 @@
@farmtoad:registry=https://repositories.communitynotfound.work/api/packages/PoliBa-Software-Architecture/npm/
//repositories.communitynotfound.work/api/packages/PoliBa-Software-Architecture/npm/:_authToken=${FarmToad_NPM}

2
.vscode/launch.json vendored
View File

@ -12,8 +12,10 @@
"cwd": "${workspaceFolder}",
"env": {},
"runtimeExecutable": "/usr/bin/deno",
"envFile": "${workspaceFolder}/.environment/.env",
"runtimeArgs": [
"run",
"--reload",
"--unstable",
"--inspect-wait",
"--allow-all"

View File

@ -4,6 +4,11 @@
},
"imports": {
"@hono/hono": "jsr:@hono/hono@^4.6.14",
"@std/assert": "jsr:@std/assert@1"
"@std/assert": "jsr:@std/assert@1",
"@types/pg": "npm:@types/pg@^8.11.10",
"drizzle-kit": "npm:drizzle-kit@^0.30.1",
"drizzle-orm": "npm:drizzle-orm@^0.38.2",
"pg": "npm:pg@^8.13.1",
"@farmtoad/farmtoad-msg-utils": "npm:@farmtoad/farmtoad-msg-utils@^0.7.2"
}
}

424
deno.lock generated
View File

@ -3,7 +3,15 @@
"specifiers": {
"jsr:@hono/hono@^4.6.14": "4.6.14",
"jsr:@std/assert@1": "1.0.9",
"jsr:@std/internal@^1.0.5": "1.0.5"
"jsr:@std/internal@^1.0.5": "1.0.5",
"npm:@farmtoad/farmtoad-msg-utils@~0.7.2": "0.7.2",
"npm:@types/node@*": "22.5.4",
"npm:@types/pg@^8.11.10": "8.11.10",
"npm:drizzle-kit@*": "0.30.1_esbuild@0.19.12",
"npm:drizzle-kit@~0.30.1": "0.30.1_esbuild@0.19.12",
"npm:drizzle-orm@*": "0.38.2_@types+pg@8.11.10_pg@8.13.1",
"npm:drizzle-orm@~0.38.2": "0.38.2_@types+pg@8.11.10_pg@8.13.1",
"npm:pg@^8.13.1": "8.13.1"
},
"jsr": {
"@hono/hono@4.6.14": {
@ -19,10 +27,422 @@
"integrity": "54a546004f769c1ac9e025abd15a76b6671ddc9687e2313b67376125650dc7ba"
}
},
"npm": {
"@deno/shim-deno-test@0.4.0": {
"integrity": "sha512-oYWcD7CpERZy/TXMTM9Tgh1HD/POHlbY9WpzmAk+5H8DohcxG415Qws8yLGlim3EaKBT2v3lJv01x4G0BosnaQ=="
},
"@deno/shim-deno@0.16.1": {
"integrity": "sha512-s9v0kzF5bm/o9TgdwvsraHx6QNllYrXXmKzgOG2lh4LFXnVMr2gpjK/c/ve6EflQn1MqImcWmVD8HAv5ahuuZQ==",
"dependencies": [
"@deno/shim-deno-test",
"which"
]
},
"@drizzle-team/brocli@0.10.2": {
"integrity": "sha512-z33Il7l5dKjUgGULTqBsQBQwckHh5AbIuxhdsIxDDiZAzBOrZO6q9ogcWC65kU382AfynTfgNumVcNIjuIua6w=="
},
"@esbuild-kit/core-utils@3.3.2": {
"integrity": "sha512-sPRAnw9CdSsRmEtnsl2WXWdyquogVpB3yZ3dgwJfe8zrOzTsV7cJvmwrKVa+0ma5BoiGJ+BoqkMvawbayKUsqQ==",
"dependencies": [
"esbuild@0.18.20",
"source-map-support"
]
},
"@esbuild-kit/esm-loader@2.6.5": {
"integrity": "sha512-FxEMIkJKnodyA1OaCUoEvbYRkoZlLZ4d/eXFu9Fh8CbBBgP5EmZxrfTRyN0qpXZ4vOvqnE5YdRdcrmUUXuU+dA==",
"dependencies": [
"@esbuild-kit/core-utils",
"get-tsconfig"
]
},
"@esbuild/aix-ppc64@0.19.12": {
"integrity": "sha512-bmoCYyWdEL3wDQIVbcyzRyeKLgk2WtWLTWz1ZIAZF/EGbNOwSA6ew3PftJ1PqMiOOGu0OyFMzG53L0zqIpPeNA=="
},
"@esbuild/android-arm64@0.18.20": {
"integrity": "sha512-Nz4rJcchGDtENV0eMKUNa6L12zz2zBDXuhj/Vjh18zGqB44Bi7MBMSXjgunJgjRhCmKOjnPuZp4Mb6OKqtMHLQ=="
},
"@esbuild/android-arm64@0.19.12": {
"integrity": "sha512-P0UVNGIienjZv3f5zq0DP3Nt2IE/3plFzuaS96vihvD0Hd6H/q4WXUGpCxD/E8YrSXfNyRPbpTq+T8ZQioSuPA=="
},
"@esbuild/android-arm@0.18.20": {
"integrity": "sha512-fyi7TDI/ijKKNZTUJAQqiG5T7YjJXgnzkURqmGj13C6dCqckZBLdl4h7bkhHt/t0WP+zO9/zwroDvANaOqO5Sw=="
},
"@esbuild/android-arm@0.19.12": {
"integrity": "sha512-qg/Lj1mu3CdQlDEEiWrlC4eaPZ1KztwGJ9B6J+/6G+/4ewxJg7gqj8eVYWvao1bXrqGiW2rsBZFSX3q2lcW05w=="
},
"@esbuild/android-x64@0.18.20": {
"integrity": "sha512-8GDdlePJA8D6zlZYJV/jnrRAi6rOiNaCC/JclcXpB+KIuvfBN4owLtgzY2bsxnx666XjJx2kDPUmnTtR8qKQUg=="
},
"@esbuild/android-x64@0.19.12": {
"integrity": "sha512-3k7ZoUW6Q6YqhdhIaq/WZ7HwBpnFBlW905Fa4s4qWJyiNOgT1dOqDiVAQFwBH7gBRZr17gLrlFCRzF6jFh7Kew=="
},
"@esbuild/darwin-arm64@0.18.20": {
"integrity": "sha512-bxRHW5kHU38zS2lPTPOyuyTm+S+eobPUnTNkdJEfAddYgEcll4xkT8DB9d2008DtTbl7uJag2HuE5NZAZgnNEA=="
},
"@esbuild/darwin-arm64@0.19.12": {
"integrity": "sha512-B6IeSgZgtEzGC42jsI+YYu9Z3HKRxp8ZT3cqhvliEHovq8HSX2YX8lNocDn79gCKJXOSaEot9MVYky7AKjCs8g=="
},
"@esbuild/darwin-x64@0.18.20": {
"integrity": "sha512-pc5gxlMDxzm513qPGbCbDukOdsGtKhfxD1zJKXjCCcU7ju50O7MeAZ8c4krSJcOIJGFR+qx21yMMVYwiQvyTyQ=="
},
"@esbuild/darwin-x64@0.19.12": {
"integrity": "sha512-hKoVkKzFiToTgn+41qGhsUJXFlIjxI/jSYeZf3ugemDYZldIXIxhvwN6erJGlX4t5h417iFuheZ7l+YVn05N3A=="
},
"@esbuild/freebsd-arm64@0.18.20": {
"integrity": "sha512-yqDQHy4QHevpMAaxhhIwYPMv1NECwOvIpGCZkECn8w2WFHXjEwrBn3CeNIYsibZ/iZEUemj++M26W3cNR5h+Tw=="
},
"@esbuild/freebsd-arm64@0.19.12": {
"integrity": "sha512-4aRvFIXmwAcDBw9AueDQ2YnGmz5L6obe5kmPT8Vd+/+x/JMVKCgdcRwH6APrbpNXsPz+K653Qg8HB/oXvXVukA=="
},
"@esbuild/freebsd-x64@0.18.20": {
"integrity": "sha512-tgWRPPuQsd3RmBZwarGVHZQvtzfEBOreNuxEMKFcd5DaDn2PbBxfwLcj4+aenoh7ctXcbXmOQIn8HI6mCSw5MQ=="
},
"@esbuild/freebsd-x64@0.19.12": {
"integrity": "sha512-EYoXZ4d8xtBoVN7CEwWY2IN4ho76xjYXqSXMNccFSx2lgqOG/1TBPW0yPx1bJZk94qu3tX0fycJeeQsKovA8gg=="
},
"@esbuild/linux-arm64@0.18.20": {
"integrity": "sha512-2YbscF+UL7SQAVIpnWvYwM+3LskyDmPhe31pE7/aoTMFKKzIc9lLbyGUpmmb8a8AixOL61sQ/mFh3jEjHYFvdA=="
},
"@esbuild/linux-arm64@0.19.12": {
"integrity": "sha512-EoTjyYyLuVPfdPLsGVVVC8a0p1BFFvtpQDB/YLEhaXyf/5bczaGeN15QkR+O4S5LeJ92Tqotve7i1jn35qwvdA=="
},
"@esbuild/linux-arm@0.18.20": {
"integrity": "sha512-/5bHkMWnq1EgKr1V+Ybz3s1hWXok7mDFUMQ4cG10AfW3wL02PSZi5kFpYKrptDsgb2WAJIvRcDm+qIvXf/apvg=="
},
"@esbuild/linux-arm@0.19.12": {
"integrity": "sha512-J5jPms//KhSNv+LO1S1TX1UWp1ucM6N6XuL6ITdKWElCu8wXP72l9MM0zDTzzeikVyqFE6U8YAV9/tFyj0ti+w=="
},
"@esbuild/linux-ia32@0.18.20": {
"integrity": "sha512-P4etWwq6IsReT0E1KHU40bOnzMHoH73aXp96Fs8TIT6z9Hu8G6+0SHSw9i2isWrD2nbx2qo5yUqACgdfVGx7TA=="
},
"@esbuild/linux-ia32@0.19.12": {
"integrity": "sha512-Thsa42rrP1+UIGaWz47uydHSBOgTUnwBwNq59khgIwktK6x60Hivfbux9iNR0eHCHzOLjLMLfUMLCypBkZXMHA=="
},
"@esbuild/linux-loong64@0.18.20": {
"integrity": "sha512-nXW8nqBTrOpDLPgPY9uV+/1DjxoQ7DoB2N8eocyq8I9XuqJ7BiAMDMf9n1xZM9TgW0J8zrquIb/A7s3BJv7rjg=="
},
"@esbuild/linux-loong64@0.19.12": {
"integrity": "sha512-LiXdXA0s3IqRRjm6rV6XaWATScKAXjI4R4LoDlvO7+yQqFdlr1Bax62sRwkVvRIrwXxvtYEHHI4dm50jAXkuAA=="
},
"@esbuild/linux-mips64el@0.18.20": {
"integrity": "sha512-d5NeaXZcHp8PzYy5VnXV3VSd2D328Zb+9dEq5HE6bw6+N86JVPExrA6O68OPwobntbNJ0pzCpUFZTo3w0GyetQ=="
},
"@esbuild/linux-mips64el@0.19.12": {
"integrity": "sha512-fEnAuj5VGTanfJ07ff0gOA6IPsvrVHLVb6Lyd1g2/ed67oU1eFzL0r9WL7ZzscD+/N6i3dWumGE1Un4f7Amf+w=="
},
"@esbuild/linux-ppc64@0.18.20": {
"integrity": "sha512-WHPyeScRNcmANnLQkq6AfyXRFr5D6N2sKgkFo2FqguP44Nw2eyDlbTdZwd9GYk98DZG9QItIiTlFLHJHjxP3FA=="
},
"@esbuild/linux-ppc64@0.19.12": {
"integrity": "sha512-nYJA2/QPimDQOh1rKWedNOe3Gfc8PabU7HT3iXWtNUbRzXS9+vgB0Fjaqr//XNbd82mCxHzik2qotuI89cfixg=="
},
"@esbuild/linux-riscv64@0.18.20": {
"integrity": "sha512-WSxo6h5ecI5XH34KC7w5veNnKkju3zBRLEQNY7mv5mtBmrP/MjNBCAlsM2u5hDBlS3NGcTQpoBvRzqBcRtpq1A=="
},
"@esbuild/linux-riscv64@0.19.12": {
"integrity": "sha512-2MueBrlPQCw5dVJJpQdUYgeqIzDQgw3QtiAHUC4RBz9FXPrskyyU3VI1hw7C0BSKB9OduwSJ79FTCqtGMWqJHg=="
},
"@esbuild/linux-s390x@0.18.20": {
"integrity": "sha512-+8231GMs3mAEth6Ja1iK0a1sQ3ohfcpzpRLH8uuc5/KVDFneH6jtAJLFGafpzpMRO6DzJ6AvXKze9LfFMrIHVQ=="
},
"@esbuild/linux-s390x@0.19.12": {
"integrity": "sha512-+Pil1Nv3Umes4m3AZKqA2anfhJiVmNCYkPchwFJNEJN5QxmTs1uzyy4TvmDrCRNT2ApwSari7ZIgrPeUx4UZDg=="
},
"@esbuild/linux-x64@0.18.20": {
"integrity": "sha512-UYqiqemphJcNsFEskc73jQ7B9jgwjWrSayxawS6UVFZGWrAAtkzjxSqnoclCXxWtfwLdzU+vTpcNYhpn43uP1w=="
},
"@esbuild/linux-x64@0.19.12": {
"integrity": "sha512-B71g1QpxfwBvNrfyJdVDexenDIt1CiDN1TIXLbhOw0KhJzE78KIFGX6OJ9MrtC0oOqMWf+0xop4qEU8JrJTwCg=="
},
"@esbuild/netbsd-x64@0.18.20": {
"integrity": "sha512-iO1c++VP6xUBUmltHZoMtCUdPlnPGdBom6IrO4gyKPFFVBKioIImVooR5I83nTew5UOYrk3gIJhbZh8X44y06A=="
},
"@esbuild/netbsd-x64@0.19.12": {
"integrity": "sha512-3ltjQ7n1owJgFbuC61Oj++XhtzmymoCihNFgT84UAmJnxJfm4sYCiSLTXZtE00VWYpPMYc+ZQmB6xbSdVh0JWA=="
},
"@esbuild/openbsd-x64@0.18.20": {
"integrity": "sha512-e5e4YSsuQfX4cxcygw/UCPIEP6wbIL+se3sxPdCiMbFLBWu0eiZOJ7WoD+ptCLrmjZBK1Wk7I6D/I3NglUGOxg=="
},
"@esbuild/openbsd-x64@0.19.12": {
"integrity": "sha512-RbrfTB9SWsr0kWmb9srfF+L933uMDdu9BIzdA7os2t0TXhCRjrQyCeOt6wVxr79CKD4c+p+YhCj31HBkYcXebw=="
},
"@esbuild/sunos-x64@0.18.20": {
"integrity": "sha512-kDbFRFp0YpTQVVrqUd5FTYmWo45zGaXe0X8E1G/LKFC0v8x0vWrhOWSLITcCn63lmZIxfOMXtCfti/RxN/0wnQ=="
},
"@esbuild/sunos-x64@0.19.12": {
"integrity": "sha512-HKjJwRrW8uWtCQnQOz9qcU3mUZhTUQvi56Q8DPTLLB+DawoiQdjsYq+j+D3s9I8VFtDr+F9CjgXKKC4ss89IeA=="
},
"@esbuild/win32-arm64@0.18.20": {
"integrity": "sha512-ddYFR6ItYgoaq4v4JmQQaAI5s7npztfV4Ag6NrhiaW0RrnOXqBkgwZLofVTlq1daVTQNhtI5oieTvkRPfZrePg=="
},
"@esbuild/win32-arm64@0.19.12": {
"integrity": "sha512-URgtR1dJnmGvX864pn1B2YUYNzjmXkuJOIqG2HdU62MVS4EHpU2946OZoTMnRUHklGtJdJZ33QfzdjGACXhn1A=="
},
"@esbuild/win32-ia32@0.18.20": {
"integrity": "sha512-Wv7QBi3ID/rROT08SABTS7eV4hX26sVduqDOTe1MvGMjNd3EjOz4b7zeexIR62GTIEKrfJXKL9LFxTYgkyeu7g=="
},
"@esbuild/win32-ia32@0.19.12": {
"integrity": "sha512-+ZOE6pUkMOJfmxmBZElNOx72NKpIa/HFOMGzu8fqzQJ5kgf6aTGrcJaFsNiVMH4JKpMipyK+7k0n2UXN7a8YKQ=="
},
"@esbuild/win32-x64@0.18.20": {
"integrity": "sha512-kTdfRcSiDfQca/y9QIkng02avJ+NCaQvrMejlsB3RRv5sE9rRoeBPISaZpKxHELzRxZyLvNts1P27W3wV+8geQ=="
},
"@esbuild/win32-x64@0.19.12": {
"integrity": "sha512-T1QyPSDCyMXaO3pzBkF96E8xMkiRYbUEZADd29SyPGabqxMViNoii+NcK7eWJAEoU6RZyEm5lVSIjTmcdoB9HA=="
},
"@farmtoad/farmtoad-msg-utils@0.7.2": {
"integrity": "sha512-NmwDwSqPP91cM8KzPAhZt/0NbUbuv91o8DhDgO/qiffDBkuw1e6sF5VlLUR9WyKQFQzb+lV2eIQrJPvbvu8HQQ==",
"dependencies": [
"@deno/shim-deno"
]
},
"@types/node@22.5.4": {
"integrity": "sha512-FDuKUJQm/ju9fT/SeX/6+gBzoPzlVCzfzmGkwKvRHQVxi4BntVbyIwf6a4Xn62mrvndLiml6z/UBXIdEVjQLXg==",
"dependencies": [
"undici-types"
]
},
"@types/pg@8.11.10": {
"integrity": "sha512-LczQUW4dbOQzsH2RQ5qoeJ6qJPdrcM/DcMLoqWQkMLMsq83J5lAX3LXjdkWdpscFy67JSOWDnh7Ny/sPFykmkg==",
"dependencies": [
"@types/node",
"pg-protocol",
"pg-types@4.0.2"
]
},
"buffer-from@1.1.2": {
"integrity": "sha512-E+XQCRwSbaaiChtv6k6Dwgc+bx+Bs6vuKJHHl5kox/BaKbhiXzqQOwK4cO22yElGp2OCmjwVhT3HmxgyPGnJfQ=="
},
"debug@4.4.0": {
"integrity": "sha512-6WTZ/IxCY/T6BALoZHaE4ctp9xm+Z5kY/pzYaCHRFeyVhojxlrm+46y68HA6hr0TcwEssoxNiDEUJQjfPZ/RYA==",
"dependencies": [
"ms"
]
},
"drizzle-kit@0.30.1_esbuild@0.19.12": {
"integrity": "sha512-HmA/NeewvHywhJ2ENXD3KvOuM/+K2dGLJfxVfIHsGwaqKICJnS+Ke2L6UcSrSrtMJLJaT0Im1Qv4TFXfaZShyw==",
"dependencies": [
"@drizzle-team/brocli",
"@esbuild-kit/esm-loader",
"esbuild@0.19.12",
"esbuild-register"
]
},
"drizzle-orm@0.38.2_@types+pg@8.11.10_pg@8.13.1": {
"integrity": "sha512-eCE3yPRAskLo1WpM9OHpFaM70tBEDsWhwR/0M3CKyztAXKR9Qs3asZlcJOEliIcUSg8GuwrlY0dmYDgmm6y5GQ==",
"dependencies": [
"@types/pg",
"pg"
]
},
"esbuild-register@3.6.0_esbuild@0.19.12": {
"integrity": "sha512-H2/S7Pm8a9CL1uhp9OvjwrBh5Pvx0H8qVOxNu8Wed9Y7qv56MPtq+GGM8RJpq6glYJn9Wspr8uw7l55uyinNeg==",
"dependencies": [
"debug",
"esbuild@0.19.12"
]
},
"esbuild@0.18.20": {
"integrity": "sha512-ceqxoedUrcayh7Y7ZX6NdbbDzGROiyVBgC4PriJThBKSVPWnnFHZAkfI1lJT8QFkOwH4qOS2SJkS4wvpGl8BpA==",
"dependencies": [
"@esbuild/android-arm@0.18.20",
"@esbuild/android-arm64@0.18.20",
"@esbuild/android-x64@0.18.20",
"@esbuild/darwin-arm64@0.18.20",
"@esbuild/darwin-x64@0.18.20",
"@esbuild/freebsd-arm64@0.18.20",
"@esbuild/freebsd-x64@0.18.20",
"@esbuild/linux-arm@0.18.20",
"@esbuild/linux-arm64@0.18.20",
"@esbuild/linux-ia32@0.18.20",
"@esbuild/linux-loong64@0.18.20",
"@esbuild/linux-mips64el@0.18.20",
"@esbuild/linux-ppc64@0.18.20",
"@esbuild/linux-riscv64@0.18.20",
"@esbuild/linux-s390x@0.18.20",
"@esbuild/linux-x64@0.18.20",
"@esbuild/netbsd-x64@0.18.20",
"@esbuild/openbsd-x64@0.18.20",
"@esbuild/sunos-x64@0.18.20",
"@esbuild/win32-arm64@0.18.20",
"@esbuild/win32-ia32@0.18.20",
"@esbuild/win32-x64@0.18.20"
]
},
"esbuild@0.19.12": {
"integrity": "sha512-aARqgq8roFBj054KvQr5f1sFu0D65G+miZRCuJyJ0G13Zwx7vRar5Zhn2tkQNzIXcBrNVsv/8stehpj+GAjgbg==",
"dependencies": [
"@esbuild/aix-ppc64",
"@esbuild/android-arm@0.19.12",
"@esbuild/android-arm64@0.19.12",
"@esbuild/android-x64@0.19.12",
"@esbuild/darwin-arm64@0.19.12",
"@esbuild/darwin-x64@0.19.12",
"@esbuild/freebsd-arm64@0.19.12",
"@esbuild/freebsd-x64@0.19.12",
"@esbuild/linux-arm@0.19.12",
"@esbuild/linux-arm64@0.19.12",
"@esbuild/linux-ia32@0.19.12",
"@esbuild/linux-loong64@0.19.12",
"@esbuild/linux-mips64el@0.19.12",
"@esbuild/linux-ppc64@0.19.12",
"@esbuild/linux-riscv64@0.19.12",
"@esbuild/linux-s390x@0.19.12",
"@esbuild/linux-x64@0.19.12",
"@esbuild/netbsd-x64@0.19.12",
"@esbuild/openbsd-x64@0.19.12",
"@esbuild/sunos-x64@0.19.12",
"@esbuild/win32-arm64@0.19.12",
"@esbuild/win32-ia32@0.19.12",
"@esbuild/win32-x64@0.19.12"
]
},
"get-tsconfig@4.8.1": {
"integrity": "sha512-k9PN+cFBmaLWtVz29SkUoqU5O0slLuHJXt/2P+tMVFT+phsSGXGkp9t3rQIqdz0e+06EHNGs3oM6ZX1s2zHxRg==",
"dependencies": [
"resolve-pkg-maps"
]
},
"isexe@2.0.0": {
"integrity": "sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw=="
},
"ms@2.1.3": {
"integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA=="
},
"obuf@1.1.2": {
"integrity": "sha512-PX1wu0AmAdPqOL1mWhqmlOd8kOIZQwGZw6rh7uby9fTc5lhaOWFLX3I6R1hrF9k3zUY40e6igsLGkDXK92LJNg=="
},
"pg-cloudflare@1.1.1": {
"integrity": "sha512-xWPagP/4B6BgFO+EKz3JONXv3YDgvkbVrGw2mTo3D6tVDQRh1e7cqVGvyR3BE+eQgAvx1XhW/iEASj4/jCWl3Q=="
},
"pg-connection-string@2.7.0": {
"integrity": "sha512-PI2W9mv53rXJQEOb8xNR8lH7Hr+EKa6oJa38zsK0S/ky2er16ios1wLKhZyxzD7jUReiWokc9WK5nxSnC7W1TA=="
},
"pg-int8@1.0.1": {
"integrity": "sha512-WCtabS6t3c8SkpDBUlb1kjOs7l66xsGdKpIPZsg4wR+B3+u9UAum2odSsF9tnvxg80h4ZxLWMy4pRjOsFIqQpw=="
},
"pg-numeric@1.0.2": {
"integrity": "sha512-BM/Thnrw5jm2kKLE5uJkXqqExRUY/toLHda65XgFTBTFYZyopbKjBe29Ii3RbkvlsMoFwD+tHeGaCjjv0gHlyw=="
},
"pg-pool@3.7.0_pg@8.13.1": {
"integrity": "sha512-ZOBQForurqh4zZWjrgSwwAtzJ7QiRX0ovFkZr2klsen3Nm0aoh33Ls0fzfv3imeH/nw/O27cjdz5kzYJfeGp/g==",
"dependencies": [
"pg"
]
},
"pg-protocol@1.7.0": {
"integrity": "sha512-hTK/mE36i8fDDhgDFjy6xNOG+LCorxLG3WO17tku+ij6sVHXh1jQUJ8hYAnRhNla4QVD2H8er/FOjc/+EgC6yQ=="
},
"pg-types@2.2.0": {
"integrity": "sha512-qTAAlrEsl8s4OiEQY69wDvcMIdQN6wdz5ojQiOy6YRMuynxenON0O5oCpJI6lshc6scgAY8qvJ2On/p+CXY0GA==",
"dependencies": [
"pg-int8",
"postgres-array@2.0.0",
"postgres-bytea@1.0.0",
"postgres-date@1.0.7",
"postgres-interval@1.2.0"
]
},
"pg-types@4.0.2": {
"integrity": "sha512-cRL3JpS3lKMGsKaWndugWQoLOCoP+Cic8oseVcbr0qhPzYD5DWXK+RZ9LY9wxRf7RQia4SCwQlXk0q6FCPrVng==",
"dependencies": [
"pg-int8",
"pg-numeric",
"postgres-array@3.0.2",
"postgres-bytea@3.0.0",
"postgres-date@2.1.0",
"postgres-interval@3.0.0",
"postgres-range"
]
},
"pg@8.13.1": {
"integrity": "sha512-OUir1A0rPNZlX//c7ksiu7crsGZTKSOXJPgtNiHGIlC9H0lO+NC6ZDYksSgBYY/thSWhnSRBv8w1lieNNGATNQ==",
"dependencies": [
"pg-cloudflare",
"pg-connection-string",
"pg-pool",
"pg-protocol",
"pg-types@2.2.0",
"pgpass"
]
},
"pgpass@1.0.5": {
"integrity": "sha512-FdW9r/jQZhSeohs1Z3sI1yxFQNFvMcnmfuj4WBMUTxOrAyLMaTcE1aAMBiTlbMNaXvBCQuVi0R7hd8udDSP7ug==",
"dependencies": [
"split2"
]
},
"postgres-array@2.0.0": {
"integrity": "sha512-VpZrUqU5A69eQyW2c5CA1jtLecCsN2U/bD6VilrFDWq5+5UIEVO7nazS3TEcHf1zuPYO/sqGvUvW62g86RXZuA=="
},
"postgres-array@3.0.2": {
"integrity": "sha512-6faShkdFugNQCLwucjPcY5ARoW1SlbnrZjmGl0IrrqewpvxvhSLHimCVzqeuULCbG0fQv7Dtk1yDbG3xv7Veog=="
},
"postgres-bytea@1.0.0": {
"integrity": "sha512-xy3pmLuQqRBZBXDULy7KbaitYqLcmxigw14Q5sj8QBVLqEwXfeybIKVWiqAXTlcvdvb0+xkOtDbfQMOf4lST1w=="
},
"postgres-bytea@3.0.0": {
"integrity": "sha512-CNd4jim9RFPkObHSjVHlVrxoVQXz7quwNFpz7RY1okNNme49+sVyiTvTRobiLV548Hx/hb1BG+iE7h9493WzFw==",
"dependencies": [
"obuf"
]
},
"postgres-date@1.0.7": {
"integrity": "sha512-suDmjLVQg78nMK2UZ454hAG+OAW+HQPZ6n++TNDUX+L0+uUlLywnoxJKDou51Zm+zTCjrCl0Nq6J9C5hP9vK/Q=="
},
"postgres-date@2.1.0": {
"integrity": "sha512-K7Juri8gtgXVcDfZttFKVmhglp7epKb1K4pgrkLxehjqkrgPhfG6OO8LHLkfaqkbpjNRnra018XwAr1yQFWGcA=="
},
"postgres-interval@1.2.0": {
"integrity": "sha512-9ZhXKM/rw350N1ovuWHbGxnGh/SNJ4cnxHiM0rxE4VN41wsg8P8zWn9hv/buK00RP4WvlOyr/RBDiptyxVbkZQ==",
"dependencies": [
"xtend"
]
},
"postgres-interval@3.0.0": {
"integrity": "sha512-BSNDnbyZCXSxgA+1f5UU2GmwhoI0aU5yMxRGO8CdFEcY2BQF9xm/7MqKnYoM1nJDk8nONNWDk9WeSmePFhQdlw=="
},
"postgres-range@1.1.4": {
"integrity": "sha512-i/hbxIE9803Alj/6ytL7UHQxRvZkI9O4Sy+J3HGc4F4oo/2eQAjTSNJ0bfxyse3bH0nuVesCk+3IRLaMtG3H6w=="
},
"resolve-pkg-maps@1.0.0": {
"integrity": "sha512-seS2Tj26TBVOC2NIc2rOe2y2ZO7efxITtLZcGSOnHHNOQ7CkiUBfw0Iw2ck6xkIhPwLhKNLS8BO+hEpngQlqzw=="
},
"source-map-support@0.5.21": {
"integrity": "sha512-uBHU3L3czsIyYXKX88fdrGovxdSCoTGDRZ6SYXtSRxLZUzHg5P/66Ht6uoUlHu9EZod+inXhKo3qQgwXUT/y1w==",
"dependencies": [
"buffer-from",
"source-map"
]
},
"source-map@0.6.1": {
"integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g=="
},
"split2@4.2.0": {
"integrity": "sha512-UcjcJOWknrNkF6PLX83qcHM6KHgVKNkV62Y8a5uYDVv9ydGQVwAHMKqHdJje1VTWpljG0WYpCDhrCdAOYH4TWg=="
},
"undici-types@6.19.8": {
"integrity": "sha512-ve2KP6f/JnbPBFyobGHuerC9g1FYGn/F8n1LWTwNxCEzd6IfqTwUQcNXgEtmmQ6DlRrC1hrSrBnCZPokRrDHjw=="
},
"which@2.0.2": {
"integrity": "sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==",
"dependencies": [
"isexe"
]
},
"xtend@4.0.2": {
"integrity": "sha512-LKYU1iAXJXUgAXn9URjiu+MWhyUXHsvfp7mcuYm9dSUKK0/CjtrUwFAxD82/mCWbtLsGjFIad0wIsod4zrTAEQ=="
}
},
"workspace": {
"dependencies": [
"jsr:@hono/hono@^4.6.14",
"jsr:@std/assert@1"
"jsr:@std/assert@1",
"npm:@farmtoad/farmtoad-msg-utils@~0.7.2",
"npm:@types/pg@^8.11.10",
"npm:drizzle-kit@~0.30.1",
"npm:drizzle-orm@~0.38.2",
"npm:pg@^8.13.1"
]
}
}

26
drizzle.config.ts Normal file
View File

@ -0,0 +1,26 @@
import { defineConfig } from "drizzle-kit";
function createConnectionString(
user: string,
password: string,
host: string,
port: string | number,
db: string
) {
return `postgresql://${user}:${password}@${host}:${port}/${db}`
}
export default defineConfig({
out: "./drizzle",
schema: "./src/db/schema/*",
dialect: "postgresql",
dbCredentials: {
url: createConnectionString(
Deno.env.get("DB_USER")!,
Deno.env.get("DB_PASSWORD")!,
Deno.env.get("DB_HOST")!,
Deno.env.get("DB_PORT")!,
Deno.env.get("DB")!
)
}
});

View File

@ -0,0 +1,13 @@
CREATE TABLE "IoT-Sensors-Data" (
"id" serial PRIMARY KEY NOT NULL,
"deviceType" integer NOT NULL,
"deviceID" integer NOT NULL,
"timestamp" date NOT NULL,
"xCoordinates" integer NOT NULL,
"yCoordinates" integer NOT NULL,
"zCoordinates" integer NOT NULL,
"dataType" text NOT NULL,
"mean_value" real NOT NULL,
"std_value" real NOT NULL,
CONSTRAINT "IoT-Sensors-Data_id_unique" UNIQUE("id")
);

View File

@ -0,0 +1,100 @@
{
"id": "92bb7aaa-a1a9-42a6-9800-74a7d19fa67b",
"prevId": "00000000-0000-0000-0000-000000000000",
"version": "7",
"dialect": "postgresql",
"tables": {
"public.IoT-Sensors-Data": {
"name": "IoT-Sensors-Data",
"schema": "",
"columns": {
"id": {
"name": "id",
"type": "serial",
"primaryKey": true,
"notNull": true
},
"deviceType": {
"name": "deviceType",
"type": "integer",
"primaryKey": false,
"notNull": true
},
"deviceID": {
"name": "deviceID",
"type": "integer",
"primaryKey": false,
"notNull": true
},
"timestamp": {
"name": "timestamp",
"type": "date",
"primaryKey": false,
"notNull": true
},
"xCoordinates": {
"name": "xCoordinates",
"type": "integer",
"primaryKey": false,
"notNull": true
},
"yCoordinates": {
"name": "yCoordinates",
"type": "integer",
"primaryKey": false,
"notNull": true
},
"zCoordinates": {
"name": "zCoordinates",
"type": "integer",
"primaryKey": false,
"notNull": true
},
"dataType": {
"name": "dataType",
"type": "text",
"primaryKey": false,
"notNull": true
},
"mean_value": {
"name": "mean_value",
"type": "real",
"primaryKey": false,
"notNull": true
},
"std_value": {
"name": "std_value",
"type": "real",
"primaryKey": false,
"notNull": true
}
},
"indexes": {},
"foreignKeys": {},
"compositePrimaryKeys": {},
"uniqueConstraints": {
"IoT-Sensors-Data_id_unique": {
"name": "IoT-Sensors-Data_id_unique",
"nullsNotDistinct": false,
"columns": [
"id"
]
}
},
"policies": {},
"checkConstraints": {},
"isRLSEnabled": false
}
},
"enums": {},
"schemas": {},
"sequences": {},
"roles": {},
"policies": {},
"views": {},
"_meta": {
"columns": {},
"schemas": {},
"tables": {}
}
}

View File

@ -0,0 +1,13 @@
{
"version": "7",
"dialect": "postgresql",
"entries": [
{
"idx": 0,
"version": "7",
"when": 1734302951810,
"tag": "0000_wide_darkhawk",
"breakpoints": true
}
]
}

View File

@ -1,7 +1,10 @@
import { Hono } from '@hono/hono'
import { iotData } from "./src/routes/Api.ts";
const app = new Hono()
app.get('/', (c) => c.text('Hello Deno!'))
Deno.serve(app.fetch)
app.route("/", iotData)
Deno.serve({port:80}, app.fetch)

View File

@ -1,6 +1,7 @@
import { assertEquals } from "@std/assert";
Deno.test(function addTest() {
});

70
src/db/db.ts Normal file
View File

@ -0,0 +1,70 @@
import { drizzle } from "drizzle-orm/node-postgres";
import { iotData as iotDataSchema } from "./schema/iot-sensors-data.schema.ts";
import pg from "pg";
import * as pgCore from "drizzle-orm/pg-core";
import { eq } from "drizzle-orm/expressions";
// Use pg driver.
const { Pool } = pg;
function createConnectionString(
user: string,
password: string,
host: string,
port: string | number,
db: string
) {
return `postgresql://${user}:${password}@${host}:${port}/${db}`
}
// Instantiate Drizzle client with pg driver and schema.
export const db = drizzle({
client: new Pool({
connectionString: createConnectionString(
Deno.env.get("DB_USER")!,
Deno.env.get("DB_PASSWORD")!,
Deno.env.get("DB_HOST")!,
Deno.env.get("DB_PORT")!,
Deno.env.get("DB")!
),
}),
schema: { iotDataSchema },
});
export type IoTDatum = typeof iotDataSchema.$inferInsert
export async function insertIoTDatum(iotDatum: typeof iotDataSchema.$inferInsert) {
return await db.insert(iotDataSchema).values(iotDatum)
}
export async function findIoTDatumByID(datumID: number) {
return await db.select().from(iotDataSchema).where(
eq(iotDataSchema.id, datumID)
)
}
// UGLY: Downcasting from bigint to number
export async function findIoTDatumByDeviceID(deviceID: bigint) {
const _deviceID: number = Number(deviceID)
return await db.select().from(iotDataSchema).where(
eq(iotDataSchema.deviceID, _deviceID)
)
}
export async function getPage(offset: number = 0, numberOfResults: number = 100) {
return await db
.select()
.from(iotDataSchema)
.orderBy(iotDataSchema.id)
.limit(numberOfResults)
.offset(offset)
}
export async function deleteIoTDatumByID(datumID: number) {
return await db.delete(iotDataSchema).where(
eq(iotDataSchema.id, datumID)
)
}

3
src/db/relations.ts Normal file
View File

@ -0,0 +1,3 @@
import { relations } from "drizzle-orm/relations";
import { } from "./schema";

View File

@ -0,0 +1,25 @@
import * as pgCore from "drizzle-orm/pg-core";
// UGLY
// UGLY: These are mockup values, but ideally, for
// UGLY: our project requirements, we should opt to use decimal
// UGLY: instead of integer and decimal serial or similar for serial.
// UGLY:
// UGLY: So these are just TOY VALUES
// UGLY:
export const iotData = pgCore.pgTable("IoT-Sensors-Data", {
id: pgCore.serial().primaryKey().notNull().unique(),
deviceType: pgCore.integer().notNull(),
deviceID: pgCore.integer().notNull(),
timestamp: pgCore.date().notNull(),
xCoordinates: pgCore.integer().notNull(),
yCoordinates: pgCore.integer().notNull(),
zCoordinates: pgCore.integer().notNull(),
dataType: pgCore.text().notNull(),
mean_value: pgCore.real().notNull(),
std_value: pgCore.real().notNull()
});
// We could in theory add the binary message, however this is just a demo

7
src/routes/Api.ts Normal file
View File

@ -0,0 +1,7 @@
import { Hono } from "@hono/hono";
import { iotDataV1 } from "./v1/iot-data.ts";
export const iotData = new Hono().basePath("/iot-data/api")
iotData.route("/", iotDataV1)

53
src/routes/v1/iot-data.ts Normal file
View File

@ -0,0 +1,53 @@
import { Hono } from "@hono/hono";
import { getPage, insertIoTDatum, IoTDatum } from "../../db/db.ts";
import { deserializerV1, DeviceType, pemString2_P256key} from "@farmtoad/farmtoad-msg-utils";
import { webcrypto } from "node:crypto";
import { iotData } from "../../db/schema/iot-sensors-data.schema.ts";
export const iotDataV1 = new Hono().basePath("/v1")
iotDataV1.get("/data", async (context) => {
const { strOffset, strNumberOfData } = context.req.query()
const offset = Number(strOffset)
const numberOfData = Number(strNumberOfData)
const page = await getPage(offset, numberOfData)
return context.json({
page: page
})
})
// TODO: have a post to insert all data inside here
iotDataV1.post("/data", async (context) => {
const KEY_DB_URL = Deno.env.get("PUBLIC_KEY_DB_URL")!
const data = await context.req.arrayBuffer()
const message = await deserializerV1(data , async (deviceType: DeviceType, deviceID: bigint) => {
const res = await fetch(`${KEY_DB_URL}/${deviceID}`)
const json = await res.json()
return await pemString2_P256key(json.publicKey)
})
// FIXME: we forget to set Fields as a map, instead of an array
// FIXME: not a big of a deal since we know the message structure
const datum : IoTDatum = {
deviceType: message.deviceType,
deviceID: Number(message.deviceID),
timestamp: new Date(message.timestamp).toISOString(),
xCoordinates: Number(message.location.x),
yCoordinates: Number(message.location.y),
zCoordinates: Number(message.location.z),
dataType: new TextDecoder().decode(message.fields[0].value),
mean_value: Number(
new TextDecoder().decode(message.fields[1].value)
),
std_value: Number(
new TextDecoder().decode(message.fields[2].value)
),
}
insertIoTDatum(datum)
})