Implement tenant CRUD operations
diff --git a/api-gateway-config/conf.d/management_apis.conf b/api-gateway-config/conf.d/management_apis.conf
index 0d9e30d..47f8ee8 100644
--- a/api-gateway-config/conf.d/management_apis.conf
+++ b/api-gateway-config/conf.d/management_apis.conf
@@ -52,6 +52,25 @@
}
}
+ location /Tenants {
+ access_by_lua_block {
+ local mgmt = require("management")
+ local requestMethod = ngx.req.get_method()
+ if requestMethod == "GET" then
+ mgmt.getTenants()
+ elseif requestMethod == "PUT" then
+ mgmt.addTenant()
+ elseif requestMethod == "POST" then
+ mgmt.addTenant()
+ elseif requestMethod == "DELETE" then
+ mgmt.deleteTenant()
+ else
+ ngx.status = 400
+ ngx.say("Invalid verb")
+ end
+ }
+ }
+
location /subscriptions {
access_by_lua_block {
local mgmt = require("management")
diff --git a/api-gateway-config/scripts/lua/lib/redis.lua b/api-gateway-config/scripts/lua/lib/redis.lua
index 7ea41b2..2687248 100644
--- a/api-gateway-config/scripts/lua/lib/redis.lua
+++ b/api-gateway-config/scripts/lua/lib/redis.lua
@@ -192,7 +192,7 @@
return resourceObj
end
---- Delete resource int redis
+--- Delete resource in redis
-- @param red redis client instance
-- @param key redis resource key
-- @param field redis resource field
@@ -213,6 +213,55 @@
end
-----------------------------
+---------- Tenants ----------
+-----------------------------
+
+--- Add tenant to redis
+-- @param red Redis client instance
+-- @param id id of tenant
+-- @param tenantObj the tenant to add
+function _M.addTenant(red, id, tenantObj)
+ local ok, err = red:hset("tenants", id, tenantObj)
+ if not ok then
+ request.err(500, utils.concatStrings({"Failed adding tenant to redis: ", err}))
+ end
+end
+
+--- Get all tenants from redis
+-- @param red Redis client instance
+function _M.getAllTenants(red)
+ local res, err = red:hgetall("tenants")
+ if not res then
+ request.err(500, utils.concatStrings({"Failed getting tenants from redis: ", err}))
+ end
+ return res
+end
+
+--- Get a single tenant from redis given its id
+-- @param redis Redis client instance
+-- @param id id of tenant to get
+function _M.getTenant(red, id)
+ local tenant, err = red:hget("tenants", id)
+ if not tenant then
+ request.err(500, utils.concatStrings({"Failed getting tenants from redis: ", err}))
+ end
+ if tenant == ngx.null then
+ request.err(404, utils.concatStrings({"Unknown tenant id ", id, "."}))
+ end
+ return cjson.decode(tenant)
+end
+
+--- Delete an tenant from redis given its id
+-- @param redis Redis client instance
+-- @param id id of tenant to delete
+function _M.deleteTenant(red, id)
+ local ok, err = red:hdel("tenants", id)
+ if not ok then
+ request.err(500, utils.concatStrings({"Failed deleting tenant from redis: ", err}))
+ end
+end
+
+-----------------------------
--- API Key Subscriptions ---
-----------------------------
diff --git a/api-gateway-config/scripts/lua/management.lua b/api-gateway-config/scripts/lua/management.lua
index 8cd3a65..6648007 100644
--- a/api-gateway-config/scripts/lua/management.lua
+++ b/api-gateway-config/scripts/lua/management.lua
@@ -42,7 +42,7 @@
--- Add an api to the Gateway
-- PUT http://0.0.0.0:9000/APIs
--- PUT JSON body:
+-- body:
-- {
-- "name": *(String) name of API
-- "basePath": *(String) base path for api
@@ -252,7 +252,95 @@
---------- Tenants ----------
-----------------------------
+--- Add a tenant to the Gateway
+-- PUT http://0.0.0.0:9000/Tenants
+-- body:
+-- {
+-- "namespace": *(String) tenant namespace
+-- "instance": *(String) tenant instance
+-- }
+function _M.addTenant()
+ -- Read in the PUT JSON Body
+ ngx.req.read_body()
+ local args = ngx.req.get_body_data()
+ if not args then
+ request.err(400, "Missing request body")
+ end
+ -- Convert json into Lua table
+ local decoded = cjson.decode(args)
+ -- Error checking
+ local fields = {"namespace", "instance"}
+ for k, v in pairs(fields) do
+ if not decoded[v] then
+ request.err(400, utils.concatStrings({"Missing field '", v, "' in request body."}))
+ end
+ end
+ -- Generate random uuid for tenant
+ local uuid = utils.uuid()
+ local tenantObj = {
+ id = uuid,
+ namespace = decoded.namespace,
+ instance = decoded.instance
+ }
+ tenantObj = cjson.encode(tenantObj)
+ local red = redis.init(REDIS_HOST, REDIS_PORT, REDIS_PASS, 1000)
+ redis.addTenant(red, uuid, tenantObj)
+ redis.close(red)
+ ngx.header.content_type = "application/json; charset=utf-8"
+ request.success(200, tenantObj)
+end
+--- Get one or all tenants from the gateway
+-- PUT http://0.0.0.0:9000/Tenants
+function _M.getTenants()
+ local uri = string.gsub(ngx.var.request_uri, "?.*", "")
+ if uri:len() <= 9 then
+ getAllTenants()
+ else
+ local id = uri:sub(10)
+ getTenant(id)
+ end
+end
+
+--- Get all tenants in redis
+function getAllTenants()
+ local red = redis.init(REDIS_HOST, REDIS_PORT, REDIS_PASS, 1000)
+ local res = redis.getAllTenants(red)
+ redis.close(red)
+ local tenantList = {}
+ for k, v in pairs(res) do
+ if k%2 == 0 then
+ tenantList[#tenantList+1] = cjson.decode(v)
+ end
+ end
+ tenantList = cjson.encode(tenantList)
+ ngx.header.content_type = "application/json; charset=utf-8"
+ request.success(200, tenantList)
+end
+
+--- Get tenant by its id
+-- @param id
+function getTenant(id)
+ local red = redis.init(REDIS_HOST, REDIS_PORT, REDIS_PASS, 1000)
+ local tenant = redis.getTenant(red, id)
+ redis.close(red)
+ ngx.header.content_type = "application/json; charset=utf-8"
+ request.success(200, cjson.encode(tenant))
+end
+
+--- Delete tenant from gateway
+-- DELETE http://0.0.0.0:9000/Tenants/<id>
+function _M.deleteTenant()
+ local uri = string.gsub(ngx.var.request_uri, "?.*", "")
+ if uri:len() <= 9 then
+ request.err(400, "No id specified.")
+ end
+ local id = uri:sub(10)
+ local red = redis.init(REDIS_HOST, REDIS_PORT, REDIS_PASS, 1000)
+ redis.deleteTenant(red, id)
+ redis.close(red)
+ request.success(200, {})
+end
------------------------------
----- Pub/Sub with Redis -----