iT邦幫忙

0

一個view使用多個model的問題

  • 分享至 

  • xImage

使用的model 1

{
    public class AreaModel : BaseModelVM 
    {
        public bool status { get; set; } //API回傳狀態,是否成功
        public List<AreaDataItem>? data { get; set; } 
    }

    public class AreaDataItem 
    {
        public string? id { get; set; } 
        public string? name { get; set; } 
        public string? kindId { get; set; } 
        public string? sort { get; set; } 
        public string? isDelete { get; set; }
        public string? createDT { get; set; }
        public string? editDT { get; set; }
        public object? deleteDT { get; set; }
    }

AreaDataItem資料來源

public class GetAreaApi
{
public static AreaModel demoJson() //這個有抓到API!!!!!!!!!!
        {

            using (WebClient wc = new WebClient())
            {

                string strURI = "";
                wc.Headers[HttpRequestHeader.ContentType] = "application/x-www-form-urlencoded";
                string area_data = wc.UploadString(strURI, "POST"); //api字串儲存在area_data

                AreaModel re_data = new AreaModel()
                {
                    status = true,
                    data = new List<AreaDataItem>(),
                };
                re_data = JsonSerializer.Deserialize<AreaModel>(area_data); //單筆資料的JSON反序列化List
                var List = re_data;
                return re_data;

            }
        }
}

model 2

public class WarehouseModel : BaseModelVM
    {
            public bool status { get; set; }
            public List<WarehouseDataItem> data { get; set; }
    }

        public class WarehouseDataItem
    {
            public string id { get; set; } 
            public string name { get; set; } 
            public string eareaid { get; set; } 
            public string kindid { get; set; } 
            public string warehouseNo { get; set; } 
            public string isDelete { get; set; }
            public string createDT { get; set; }
            public string editDT { get; set; }
            public object deleteDT { get; set; }
    }

WarehouseDataItem資料來源

public class GetWarehouseApi
    {
        public static WarehouseModel demoJson() 
        {

            using (WebClient wc1 = new WebClient())
            {

                string strURI1 = "";
                wc1.Headers[HttpRequestHeader.ContentType] = "application/x-www-form-urlencoded";
                string warehouse_data = wc1.UploadString(strURI1, "POST"); //api字串儲存在warehouse_data

                WarehouseModel re_dataw = new WarehouseModel()
                {
                    status = true,
                    data = new List<WarehouseDataItem>()
                };
                re_dataw = JsonSerializer.Deserialize<WarehouseModel>(warehouse_data); //單筆資料的JSON反序列化List
                var List = re_dataw;
                return re_dataw;

            }
        }
    }

統整上述兩個Model的BaseModelVM

public class BaseModelVM
    {
        public AreaModel Area { get; set; } //AreaModel的數據

        public WarehouseModel Warehouse { get; set; } //Warehouse的數據

    }

VIEW的部分

@using Banana.Models;
@model Banana.Models.BaseModelVM

@{
    Layout = "_Layout";
}
div class="text-center">

    <br />
    @if (Model.Area != null)
    {
        @Model.Area.status <br />

        if (Model.Area != null)
        {
            foreach (var item in Model.Area.data)
                @item.name <br/>      
        }
    }
    <br />

    @if (Model.Warehouse != null)
    {
        @Model.Warehouse.status <br />

        if (Model.Warehouse.data != null)
        {
            foreach (var item in Model.Warehouse.data)
                @item.name <br/>      
        }
    }
</div>

Controller的部分

public IActionResult Index2()
        {

            BaseModelVM vm = new BaseModelVM();
            vm.Area = new AreaModel().Area;
            vm.Warehouse = new WarehouseModel().Warehouse;
            return View(vm);
        }

最後跑出來會變這樣
https://ithelp.ithome.com.tw/upload/images/20220811/20150769Ge93DTda0R.png

想請問是哪裡出了問題呢

看更多先前的討論...收起先前的討論...
你的WarehouseModel 跟AreaModel 為什麼要繼承BaseModelVM 啊?
然後你的VIEW檔案名稱是?
我是看其他範例這樣寫的,所以是不用繼承嗎?
VIEW的檔案名稱是index2
你檔案名稱改Index2
然後不用繼承
把繼承刪掉的話 Controller會出現以下錯誤
BaseModelVM vm = new BaseModelVM();
vm.Area = new AreaModel().Area;
vm.Warehouse = new WarehouseModel().Warehouse;
return View(vm);

上面的new AreaModel().Area;的Area跟
new WarehouseModel().Warehouse;的Warehouse會變紅線
不用.Area
也不用.Warehouse
vm.Area = new AreaModel();
vm.Warehouse = new WarehouseModel();
他會變成foreach (var item in Model.Area.data)這行出問題QQ
因為你沒有初始化
你沒有資料 null 會噴錯
public class AreaModel
{
public bool status { get; set; } //API回傳狀態,是否成功
public List<AreaDataItem>? data { get; set; }
}
改成
public List<AreaDataItem>? data { get; set; } = new List<AreaDataItem>();
下面的那個MODEL同理
你要印 @item.name 至少塞個名字給他吧
我的資料來源有回覆在底下的回答 是連接到寫好的API 在反序列化成物件
那這樣還有需要加上new List<AreaDataItem>();嗎?

vm.Area = new AreaModel().Area;
vm.Area.data = demoJson();
這樣寫的話後方的Area跟demoJson()都會出現錯誤
'AreaModel' 未包含 'Area' 的定義,也找不到可接受類型
'AreaModel' 第一個引數的可存取擴充方法 'Area' (是否遺漏 using 指示詞或組件參考?)

無法將類型 'Banana.Models.AreaModel' 隱含轉換成 'System.Collections.Generic.List<Banana.Models.AreaDataItem>'
這是他的錯誤訊息
vm.Area = new AreaModel();
我多複製一個.Area
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

2 個回答

0
dpanaben
iT邦研究生 5 級 ‧ 2022-08-11 17:15:59

類似 然後上面兩個model的AreaDataItem 跟 WarehouseDataItem的資料是由呼叫API數據得來的

public static AreaModel demoJson() //這個有抓到API!!!!!!!!!!
        {

            using (WebClient wc = new WebClient())
            {

                string strURI = "";
                wc.Headers[HttpRequestHeader.ContentType] = "application/x-www-form-urlencoded";
                string area_data = wc.UploadString(strURI, "POST"); //api字串儲存在area_data

                AreaModel re_data = new AreaModel()
                {
                    status = true,
                    data = new List<AreaDataItem>(),
                };
                re_data = JsonSerializer.Deserialize<AreaModel>(area_data); //單筆資料的JSON反序列化List
                var List = re_data;
                return re_data;

            }
        }

所以還是不太知道要用甚麼方法才寫得出來

0
canrong
iT邦新手 2 級 ‧ 2022-08-11 19:52:16

public class WarehouseDataItem
{
    public string id { get; set; } 
    public string name { get; set; } 
    public string eareaid { get; set; } 
    public string kindid { get; set; } 
    public string warehouseNo { get; set; } 
    public string isDelete { get; set; }
    public string createDT { get; set; }
    public string editDT { get; set; }
    public object deleteDT { get; set; }
}

public class AreaDataItem 
{
    public string id { get; set; } 
    public string name { get; set; } 
    public string kindId { get; set; } 
    public string sort { get; set; } 
    public string isDelete { get; set; }
    public string createDT { get; set; }
    public string editDT { get; set; }
    public object deleteDT { get; set; }
}

public class BaseModelVM
{
    public List<AreaDataItem> AreaDatas { get; set; } 
    public List<WarehouseDataItem> WarehouseDatas { get; set; }
}

public IActionResult Index2()
{
    return View(new BaseModelVM{
        AreaDatas = GetAreaApi.demoJson(),
        WarehouseDatas = GetWarehouseApi.demoJson()
    });
}

public class GetWarehouseApi
{
    public static List<WarehouseDataItem> demoJson() 
    {
        using (WebClient wc1 = new WebClient())
        {
            string strURI1 = "";
            wc1.Headers[HttpRequestHeader.ContentType] = "application/x-www-form-urlencoded";
    string warehouse_data = wc1.UploadString(strURI1, "POST");
    if(string.IsNullOrEmpty(warehouse_data))
    {
        return null;
    }
    return JsonSerializer.Deserialize<List<WarehouseDataItem>>(warehouse_data);
            }
        }
    }

public class GetAreaApi
{
    public static List<AreaDataItem> demoJson()
    {
        using (WebClient wc = new WebClient())
        {
            string strURI = "";
            wc.Headers[HttpRequestHeader.ContentType] = "application/x-www-form-urlencoded";
            string area_data = wc.UploadString(strURI, "POST");
            if(string.IsNullOrEmpty(area_data))
            {
                return null;
            }
            return JsonSerializer.Deserialize<List<AreaDataItem>>(area_data);
            }
        }
}

-----------------------------------------------------------------------------
@using Banana.Models;
@model Banana.Models.BaseModelVM

@{
    Layout = "_Layout";
}
<div class="text-center">

    <br />
    @if (Model.AreaDatas != null)
    {
        foreach (AreaDataItem item in Model.AreaDatas)
        {
            @item.name <br/>      
        }
    }
    <br />

    @if (Model.WarehouseDatas != null)
    {
        foreach (WarehouseDataItem item in Model.WarehouseDatas)
        {
            @item.name <br/>      
        }
    }
</div>

沒測試過,僅針對有疑問的地方提供修改方案。

看更多先前的回應...收起先前的回應...
canrong iT邦新手 2 級 ‧ 2022-08-11 20:03:07 檢舉

原本看到標題是想請你直接使用TypeBuilder去寫,但看了一下發現你的問題跟需求可能沾不上邊。

您好 我有試出來了~
不過我BaseModelVM還是維持

public AreaModel Area { get; set; } //AreaModel的數據
public WarehouseModel Warehouse { get; set; } //Warehouse的數據

然後想請教您Controller那邊的寫法

return View
                (
                new BaseModelVM
                {
                    Area = GetAreaApi.demoJson(),
                    Warehouse = GetWarehouseApi.demoJson()
                }
                );

為什麼要這樣寫呢 小妹我是程式新手所以希望能搞懂每一句的意思 非常感謝您!!!

canrong iT邦新手 2 級 ‧ 2022-08-12 09:45:36 檢舉
BaseModelVM baseModelVM = new BaseModelVM();
baseModelVM.Area = GetAreaApi.demoJson();
baseModelVM.Warehouse = GetWarehouseApi.demoJson();
return View(baseModelVM);
BaseModelVM baseModelVM = 
new BaseModelVM
{
    Area = GetAreaApi.demoJson(),
    Warehouse = GetWarehouseApi.demoJson()
};
return View(baseModelVM);
return View(
    new BaseModelVM
    {
        Area = GetAreaApi.demoJson(),
        Warehouse = GetWarehouseApi.demoJson()
    });

算是簡寫

canrong iT邦新手 2 級 ‧ 2022-08-12 09:58:55 檢舉

算是個題外話吧,string?與object?應該會編譯錯誤才對,因為可以使用?的類別應該是default value not null例如int或者DataTime才可以使用。

string跟object是原本就寫死的json格式 所以應該才沒影響?

canrong iT邦新手 2 級 ‧ 2022-08-12 11:50:51 檢舉

這部分主要還是看各版本官方手冊的解釋,看你原本文章內的寫法,繼承與泛型的觀念可能要再了解一下。隱含轉類的錯誤是泛型使用的問題。繼承雖然那樣寫沒問題,但主要是非必要。你已經解決問題了,我就不再回復這篇文章了。

我要發表回答

立即登入回答