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

Adds shared-state rpcd data,error output format and shared-state-async rpcd reimplementation #1103

Merged
merged 2 commits into from
Apr 24, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
104 changes: 41 additions & 63 deletions packages/shared-state-async/files/usr/libexec/rpcd/shared-state-async
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Using shell instead of Lua resulted in a much nicer code as anticipated :-)

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

much better, I was worried about json parsing but some else was also worried before me.

Original file line number Diff line number Diff line change
@@ -1,63 +1,41 @@
#!/usr/bin/env lua

--[[
Shared State Async

Copyright (c) 2024 Javier Jorge <jjorge@inti.gob.ar>
Copyright (c) 2024 Instituto Nacional de Tecnolog..a Industrial
Copyright (C) 2024 Asociacion Civil Altermundi <info@altermundi.net>

This is free software, licensed under the GNU AFFERO GENERAL PUBLIC LICENSE Version 3
]]
--
local utils = require('lime.utils')
local json = require 'luci.jsonc'

local function get(msg)
local error = os.execute("shared-state-async get " ..
msg.data_type .. " 2>/dev/null ")
-- if os.execute dont fail will print the output and rpcd wont execute
-- the following lines. If there is an error the above code wont print
-- anything and this code will return the error code.
utils.printJson({
error = error
})
end

local function sync(msg)
local error = os.execute("shared-state-async sync " ..
msg.data_type .. " " .. table.concat(msg.peers_ip or {}, " ") .. " 2>/dev/null ")
utils.printJson({
error = error
})
end

--{"data_type":"data","peers_ip":["10.0.0.1","10.0.0.2"]}
--{"data_type":"data","peers_ip":["10.0.0.1"]}
local methods = {
get = {
data_type = 'value'
},
sync = {
data_type = 'value',
peers_ip = 'value'
}
}

if arg[1] == 'list' then
utils.printJson(methods)
end

if arg[1] == 'call' then
local msg = utils.rpcd_readline()
msg = json.parse(msg)
if arg[2] == 'get' then
get(msg)
elseif arg[2] == 'sync' then
sync(msg)
else
utils.printJson({
error = "Method not found"
})
end
end
#!/bin/sh

# Shared State Async
# Copyright (c) 2024 Javier Jorge <jjorge@inti.gob.ar>
# Copyright (c) 2024 Instituto Nacional de Tecnologia Industrial
# Copyright (C) 2024 Asociacion Civil Altermundi <info@altermundi.net>
# SPDX-License-Identifier: AGPL-3.0-only


sinc_args=""

case "$1" in
list)
echo '{ "sync": { "data_type": "str", "peers_ip": "str" }, "get": { "data_type": "str" } }'
;;
call)
# source jshn shell library
. /usr/share/libubox/jshn.sh
read msg
json_load $msg
json_get_vars data_type
json_get_vars peers_ip
case "$2" in
get)
if output=$(shared-state-async get $data_type 2>/dev/null)
then
echo {\"data\": $output , \"error\" :$?}
else
echo {\"data\": {} , \"error\": $? }
fi
;;
sync)
shared-state-async sync $data_type ${peers_ip//,/ } > /dev/null 2>&1
echo {\"data\": {} , \"error\": $? }
;;
*)
echo '{\"data\" {} ,\"error\" = "Method not found"}'
;;
esac
;;
esac
23 changes: 7 additions & 16 deletions packages/shared-state-async/tests/test_rpcd_shared-state-async.lua
Original file line number Diff line number Diff line change
Expand Up @@ -3,32 +3,23 @@ local sharedState = require("shared-state")
local json = require("luci.jsonc")

local testFileName = "packages/shared-state-async/files/usr/libexec/rpcd/shared-state-async"
local sharedStateRpc = testUtils.load_lua_file_as_function(testFileName)
local rpcdCall = testUtils.rpcd_call


--since there is no Shared State async binary, testing possiblities are reduced
--also testing the full
--manual testing can be done on a router with bat-hosts package using this commands:
--ubus -S call shared-state-async get "{'data_type': 'bat-hosts'}"
--ubus -S call shared-state-async sync "{'data_type': 'bat-hosts'}"
--ubus -S call shared-state-async sync "{'data_type': 'bat-hosts' ,'peers_ip':['10.0.0.1','10.0.0.2']}'"


describe('ubus-shared-state tests #ubus-shared-state', function()
before_each('', function()
testDir = testUtils.setup_test_dir()
sharedState.DATA_DIR = testDir
sharedState.PERSISTENT_DATA_DIR = testDir
end)

after_each('', function()
testUtils.teardown_test_dir()
end)

it('test list methods', function()
local response = rpcdCall(sharedStateRpc, {'list'})
assert.is.equal("value", response.get.data_type)
assert.is.equal("value", response.sync.data_type)
assert.is.equal("value", response.sync.peers_ip)

local response = utils.unsafe_shell(testFileName.." list")
response = json.parse(response)
assert.is.equal("str", response.get.data_type)
assert.is.equal("str", response.sync.data_type)
assert.is.equal("str", response.sync.peers_ip)
end)
end)
53 changes: 28 additions & 25 deletions packages/shared-state/files/usr/libexec/rpcd/shared-state
Original file line number Diff line number Diff line change
@@ -1,45 +1,48 @@
#!/usr/bin/env lua
--[[
Shared State
#!/usr/bin/env lua

Copyright (c) 2023 Javier Jorge <jjorge@inti.gob.ar>
Copyright (c) 2023 Instituto Nacional de Tecnología Industrial
Copyright (C) 2023 Asociación Civil Altermundi <info@altermundi.net>
--! Shared State
--! Copyright (c) 2023 Javier Jorge <jjorge@inti.gob.ar>
--! Copyright (c) 2023 Instituto Nacional de Tecnología Industrial
--! Copyright (C) 2023 Asociación Civil Altermundi <info@altermundi.net>
--! SPDX-License-Identifier: AGPL-3.0-only

This is free software, licensed under the GNU AFFERO GENERAL PUBLIC LICENSE Version 3
]] --
local ubus = require "ubus"
local utils = require('lime.utils')
local shared_state = require("shared-state")
local json = require 'luci.jsonc'

require("nixio.util")

local function getFromSharedState(msg)
local sharedState = shared_state.SharedState:new(msg.data_type,
nixio.syslog)
local response_template = {data = {}, error = 500}

local function showData(sharedState)
local resultTable = sharedState:get()
local response ={}
for k,v in pairs(resultTable) do
response[k]=v.data
if next(resultTable) == nill then
response_template.error = 404
else
for k, v in pairs(resultTable) do
response_template.data[k] = v.data
end
response_template.error = 0
end
utils.printJson(response)
utils.printJson(response_template)
end

local function getFromSharedState(msg)
local sharedState = shared_state.SharedState:new(msg.data_type,
nixio.syslog)
showData(sharedState)
end

local function getFromSharedStateMultiWriter(msg)
local sharedState = shared_state.SharedStateMultiWriter:new(msg.data_type,
nixio.syslog)
local resultTable = sharedState:get()
local response ={}
for k,v in pairs(resultTable) do
response[k]=v.data
end
utils.printJson(response)
local sharedState = shared_state.SharedStateMultiWriter:new(msg.data_type,
nixio.syslog)
showData(sharedState)
end

local function insertIntoSharedStateMultiWriter(msg)
local sharedState = shared_state.SharedStateMultiWriter:new(msg.data_type,
nixio.syslog)
local sharedState = shared_state.SharedStateMultiWriter:new(msg.data_type,
nixio.syslog)
local inputTable = msg.json or {}
sharedState:insert(inputTable)
end
Expand Down
40 changes: 25 additions & 15 deletions packages/shared-state/tests/test_rpcd_shared-state.lua
Original file line number Diff line number Diff line change
Expand Up @@ -38,11 +38,21 @@ describe('ubus-shared-state tests #ubus-shared-state', function()
assert.is.equal(dbA.zig.data, 'zag')
local response = rpcdCall(sharedStateRpc, {'call', 'getFromSharedState'},
'{"data_type": "wifi_links_info"}')
assert.is.equal(response.bar, 'foo')
assert.is.equal(response.baz, 'qux')
assert.is.equal(response.zig, 'zag')
assert.is.equal(response.data.bar, 'foo')
assert.is.equal(response.data.baz, 'qux')
assert.is.equal(response.data.zig, 'zag')
end)

it('test get multiwriter data from empty data_type ', function()
local sharedStateA = sharedState.SharedStateMultiWriter:new('EMPTY')

local response = rpcdCall(sharedStateRpc, {'call',
'getFromSharedStateMultiWriter'}, '{"data_type": "EMPTY"}')
assert.is.equal(response.error, 404)
assert.is.equal(next(response.data), next({}))
end)


it('test get multiwriter data ', function()
local sharedStateA = sharedState.SharedStateMultiWriter:new('A')
sharedStateA:insert({
Expand All @@ -55,9 +65,9 @@ describe('ubus-shared-state tests #ubus-shared-state', function()
assert.is.equal('zag', dbA.zig.data)
local response = rpcdCall(sharedStateRpc, {'call',
'getFromSharedStateMultiWriter'}, '{"data_type": "A"}')
assert.is.equal(response.bar, 'foo')
assert.is.equal(response.baz, 'qux')
assert.is.equal(response.zig, 'zag')
assert.is.equal(response.data.bar, 'foo')
assert.is.equal(response.data.baz, 'qux')
assert.is.equal(response.data.zig, 'zag')
end)

it('test insert multiwriter data ', function()
Expand Down Expand Up @@ -87,8 +97,8 @@ describe('ubus-shared-state tests #ubus-shared-state', function()
})
local response = rpcdCall(sharedStateRpc, {'call',
'getFromSharedStateMultiWriter'}, '{"data_type": "A"}')
assert.is.equal('foo', response.bar)
assert.is.equal('zag', response.zig)
assert.is.equal('foo', response.data.bar)
assert.is.equal('zag', response.data.zig)
response.zig="newzag"
callargs = '{"data_type": "A", "json": '..json.stringify(response)..'}'
local response = rpcdCall(sharedStateRpc, {'call',
Expand Down Expand Up @@ -143,16 +153,16 @@ describe('ubus-shared-state tests #ubus-shared-state', function()
'{"data_type": "A", "json": {"zig": "zag"}}')
response = rpcdCall(sharedStateRpc, {'call',
'getFromSharedStateMultiWriter'}, '{"data_type": "A"}')
assert.is.equal(response.zig, 'zag')
assert.is.equal(response.data.zig, 'zag')

response = rpcdCall(sharedStateRpc, {'call',
'insertIntoSharedStateMultiWriter'},
wifiStatusJsonsample23)
response = rpcdCall(sharedStateRpc, {'call',
'getFromSharedStateMultiWriter'},
'{"data_type": "ref_state_wifilinks"}')
assert.is.equal(response.primero.bleachTTL, 23)
assert.is.equal(response.primero.author, "primero")
assert.is.equal(response.data.primero.bleachTTL, 23)
assert.is.equal(response.data.primero.author, "primero")

response = rpcdCall(sharedStateRpc, {'call',
'insertIntoSharedStateMultiWriter'},wifiStatusJsonsample27)
Expand All @@ -161,16 +171,16 @@ describe('ubus-shared-state tests #ubus-shared-state', function()
'getFromSharedStateMultiWriter'},
'{"data_type": "ref_state_wifilinks"}')

assert.is.equal(response.primero.bleachTTL, 27)
assert.is.equal(response.primero.author, "primero")
assert.is.equal(response.data.primero.bleachTTL, 27)
assert.is.equal(response.data.primero.author, "primero")

response = rpcdCall(sharedStateRpc, {'call',
'insertIntoSharedStateMultiWriter'},
wifiStatusJsonsample23)
response = rpcdCall(sharedStateRpc, {'call',
'getFromSharedStateMultiWriter'},
'{"data_type": "ref_state_wifilinks"}')
assert.is.equal(response.primero.bleachTTL, 23)
assert.is.equal(response.primero.author, "primero")
assert.is.equal(response.data.primero.bleachTTL, 23)
assert.is.equal(response.data.primero.author, "primero")
end)
end)
Loading