WAF rules
Alexander Polakov edited this page Oct 25, 2021
·
2 revisions
cacherpc
supports filters written in Lua since v0.1.34. They can be used to filter requests before they're processed.
A waf module currently consists of one function waf.request(data)
where data is a structure with 3 fields:
- jsonrpc - string (jsonrpc version)
- method - string (jsonrpc request method, currently one of
getAccountInfo
orgetProgramAccounts
) - params - string (
params
field of the json request)
waf.request
must return a pair of (bool, string) where true
means request should be passed for further processing and false
means processing should be stopped returning message in the second element.
Example:
local waf = { }
local json = require 'json'
function waf.request(data)
if data.method == 'getProgramAccounts' then
--- parse parameters
local params = json.decode(data.params)
--- only interested in 9xQ... requests
if params[1] == '9xQeWvG816bUx9EPjHmaT23yvVM2ZWbrrpZb9PusVFin' then
--- options are required
if params[2] == nil then return false, 'No params' end
--- retrieve filters field
local filters = params[2].filters
if filters == nil then
return false, 'Rejected for no filters'
else
--- setup filter counters
local counts = { memcmp = 0, dataSize = 0 }
--- iterate over filters
for i,filter in ipairs(filters) do
for name, _ in pairs(filter) do
counts[name] = counts[name] + 1
end
end
--- pass if both filters found
if counts.memcmp > 0 and counts.dataSize > 0 then
return true, ''
else
return false, 'Rejected for no data_size/memcmp'
end
end
end
end
return true, ''
end
return waf
To test filters without running cacherpc
one can use a local lua interpreter with test data.
Put your waf code in waf.lua
file, get json.lua and put it in the same directory.
Then start lua:
$ lua
Lua 5.4.2 Copyright (C) 1994-2020 Lua.org, PUC-Rio
> json = require 'json'
> waf = require 'waf'
> --- provide test data
> r = { method = 'getProgramAccounts', params = '["9xQeWvG816bUx9EPjHmaT23yvVM2ZWbrrpZb9PusVFin",{"commitment":"confirmed","filters":[{"memcmp":{"offset":13,"bytes":"3hwH1txjJVS8qv588tWrjHfRxdqNjBykM1kMcit484up"}},{"memcmp":{"offset":45,"bytes":"DgfZuKR4NcVhqnwcmMFxVSf58z32NwuYdhyAekNKNofh"}},{"dataSize":3228}],"encoding":"base64"}]' }
> --- call request
> print(waf.request(r))
true
as we can see it returns true as expected