-- Copyright (c) 2024 Huawei Technologies Co., Ltd.
-- openUBMC is licensed under Mulan PSL v2.
-- You can use this software according to the terms and conditions of the Mulan PSL v2.
-- You may obtain a copy of Mulan PSL v2 at:
--         http://license.coscl.org.cn/MulanPSL2
-- THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND,
-- EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT,
-- MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
-- See the Mulan PSL v2 for more details.

local validate = require 'mc.validate'
local utils = require 'mc.utils'

local msg = {}
local defs = {}

---@class defs.a3Struct1
---@field a2 integer[]
---@field a3 string
local Ta3Struct1 = {}
Ta3Struct1.__index = Ta3Struct1
Ta3Struct1.group = {}

local function Ta3Struct1_from_obj(obj)
    return setmetatable(obj, Ta3Struct1)
end

function Ta3Struct1.new(a2, a3)
    return Ta3Struct1_from_obj({a2 = a2, a3 = a3})
end
---@param obj defs.a3Struct1
function Ta3Struct1:init_from_obj(obj)
    self.a2 = obj.a2
    self.a3 = obj.a3
end

function Ta3Struct1:remove_error_props(errs, obj)
    utils.remove_obj_error_property(obj, errs, Ta3Struct1.group)
end

Ta3Struct1.from_obj = Ta3Struct1_from_obj

Ta3Struct1.proto_property = {'a2', 'a3'}

Ta3Struct1.default = {{}, ''}

Ta3Struct1.struct = {
    {name = 'a2', is_array = true, struct = nil}, {name = 'a3', is_array = false, struct = nil}
}

function Ta3Struct1:validate(prefix, errs)
    prefix = prefix or ''

    validate.RequiredArray(prefix .. 'a2', self.a2, 'int64', false, errs)
    validate.Required(prefix .. 'a3', self.a3, 'string', false, errs)

    Ta3Struct1:remove_error_props(errs, self)
    validate.CheckUnknowProperty(self, Ta3Struct1.proto_property, errs)
    return self
end

function Ta3Struct1:unpack(_)
    return self.a2, self.a3
end

defs.a3Struct1 = Ta3Struct1

---@class defs.reqStruct1
---@field a2 boolean
---@field a3 defs.a3Struct1
local TreqStruct1 = {}
TreqStruct1.__index = TreqStruct1
TreqStruct1.group = {}

local function TreqStruct1_from_obj(obj)
    obj.a3 = utils.from_obj(defs.a3Struct1, obj.a3)
    return setmetatable(obj, TreqStruct1)
end

function TreqStruct1.new(a2, a3)
    return TreqStruct1_from_obj({a2 = a2, a3 = a3})
end
---@param obj defs.reqStruct1
function TreqStruct1:init_from_obj(obj)
    self.a2 = obj.a2
    self.a3 = obj.a3
end

function TreqStruct1:remove_error_props(errs, obj)
    utils.remove_obj_error_property(obj, errs, TreqStruct1.group)
end

TreqStruct1.from_obj = TreqStruct1_from_obj

TreqStruct1.proto_property = {'a2', 'a3'}

TreqStruct1.default = {false, defs.a3Struct1.default}

TreqStruct1.struct = {
    {name = 'a2', is_array = false, struct = nil},
    {name = 'a3', is_array = false, struct = defs.a3Struct1.struct}
}

function TreqStruct1:validate(prefix, errs)
    prefix = prefix or ''

    validate.Required(prefix .. 'a2', self.a2, 'bool', false, errs)
    validate.Required(prefix .. 'a3', self.a3, 'defs.a3Struct1', false, errs)

    TreqStruct1:remove_error_props(errs, self)
    validate.CheckUnknowProperty(self, TreqStruct1.proto_property, errs)
    return self
end

function TreqStruct1:unpack(raw)
    return self.a2, utils.unpack(raw, self.a3)
end

defs.reqStruct1 = TreqStruct1

---@class IDemo.Method1Rsp
---@field r1 integer
local TMethod1Rsp = {}
TMethod1Rsp.__index = TMethod1Rsp
TMethod1Rsp.group = {}

local function TMethod1Rsp_from_obj(obj)
    return setmetatable(obj, TMethod1Rsp)
end

function TMethod1Rsp.new(r1)
    return TMethod1Rsp_from_obj({r1 = r1})
end
---@param obj IDemo.Method1Rsp
function TMethod1Rsp:init_from_obj(obj)
    self.r1 = obj.r1
end

function TMethod1Rsp:remove_error_props(errs, obj)
    utils.remove_obj_error_property(obj, errs, TMethod1Rsp.group)
end

TMethod1Rsp.from_obj = TMethod1Rsp_from_obj

TMethod1Rsp.proto_property = {'r1'}

TMethod1Rsp.default = {0}

TMethod1Rsp.struct = {{name = 'r1', is_array = false, struct = nil}}

function TMethod1Rsp:validate(prefix, errs)
    prefix = prefix or ''

    validate.Required(prefix .. 'r1', self.r1, 'uint16', false, errs)

    TMethod1Rsp:remove_error_props(errs, self)
    validate.CheckUnknowProperty(self, TMethod1Rsp.proto_property, errs)
    return self
end

function TMethod1Rsp:unpack(_)
    return self.r1
end

msg.Method1Rsp = TMethod1Rsp

---@class IDemo.Method1Req
---@field a1 integer
---@field s1 defs.reqStruct1[]
local TMethod1Req = {}
TMethod1Req.__index = TMethod1Req
TMethod1Req.group = {}

local function TMethod1Req_from_obj(obj)
    obj.s1 = utils.from_obj(defs.reqStruct1, obj.s1, true)
    return setmetatable(obj, TMethod1Req)
end

function TMethod1Req.new(a1, s1)
    return TMethod1Req_from_obj({a1 = a1, s1 = s1})
end
---@param obj IDemo.Method1Req
function TMethod1Req:init_from_obj(obj)
    self.a1 = obj.a1
    self.s1 = obj.s1
end

function TMethod1Req:remove_error_props(errs, obj)
    utils.remove_obj_error_property(obj, errs, TMethod1Req.group)
end

TMethod1Req.from_obj = TMethod1Req_from_obj

TMethod1Req.proto_property = {'a1', 's1'}

TMethod1Req.default = {0, {}}

TMethod1Req.struct = {
    {name = 'a1', is_array = false, struct = nil},
    {name = 's1', is_array = true, struct = defs.reqStruct1.struct}
}

function TMethod1Req:validate(prefix, errs)
    prefix = prefix or ''

    validate.Required(prefix .. 'a1', self.a1, 'uint8', false, errs)
    validate.RequiredArray(prefix .. 's1', self.s1, 'defs.reqStruct1', false, errs)

    TMethod1Req:remove_error_props(errs, self)
    validate.CheckUnknowProperty(self, TMethod1Req.proto_property, errs)
    return self
end

function TMethod1Req:unpack(raw)
    return self.a1, utils.unpack(raw, self.s1, true)
end

msg.Method1Req = TMethod1Req

local IDemo = {}

local Mdb = require 'mc.mdb'

---@class IDemo: Table
---@field p1 integer
---@field priority integer
IDemo.IDemo = Mdb.register_interface('bmc.demo.IDemo',
    {p1 = {'y', nil, false, 0}, priority = {'y', nil, true, nil}}, {
        Method1 = {'a{ss}ya(b(axs))', 'q', msg.Method1Req, msg.Method1Rsp}
    }, {})
return IDemo
