0

私はクライアントサーバー、SQLプログラマー(RAD担当者)であり、会社は.NET環境に移行する必要があると判断しました。現在、プラットフォームを検討しています。

今週はMVC4とEntitiesFrameworkを勉強し、KendoUIについてたくさん読みました。ほとんどの例にはKendoGrid+WebApiが付属しているため、私は懐疑的でした。私はWebApiについてほとんど知りませんが、エンティティのことをとても気に入っていたので、チャンスを与えるべきではないと思います。

素朴に見えるかもしれない質問をしたいのですが、答えは私を大いに助けてくれます

  1. 既存のデータベースからエンティティを作成したら、結果をJson形式で取得し、これを使用してKendoGridにフィードできますか?

    はいの場合、どのように?つまり:

  2. コントローラ内のJsonで結果を変換するにはどうすればよいですか?

  3. KendoGridのトランスポートプロパティに、コントローラー/アクションのURLを入力する必要がありますか?

    そして最も素朴なもの

  4. Telerikは、kendoGridを作成-構成するためのビジュアルツールを提供することを考えていますか?あまりにも多くのコーディングが必要なため、RADを増やすには。おそらく、エンティティをグリッド列、データソース、トランスポートセレクターなどに接続できるウィザードです。

4

2 に答える 2

3

剣道エンティティのパスを選択していただければ幸いですが、学習曲線はあります。いいえ、質問4です。しかし、Razorビューエンジンを使用してジャンプスタートを行い、1、2、および3に答えましょう。

まず、EFはビジネスオブジェクトを作成しています。これらをMVCのモデルに変換する必要があります。この例では、PersonはEFの出身です。データベースがそのように設定されている場合は、Person.Titles.Nameのようなものを参照できるようにまだ利用可能ですが、オブジェクトから深さを削除するため、これは平坦化と考えています。また、DataAnnotationsにドロップすることもできます。

using System.Collections.Generic;
using System.ComponentModel.DataAnnotations;
using System.Linq;
using Project.Business;

namespace Project.Web.Models
{
    public class PersonModel
    {
        public int Id { get; set; }
        [Required(ErrorMessage = "Last Name is required.")]
        public string LastName { get; set; }
        [Required(ErrorMessage = "First Name is required.")]
        public string FirstName { get; set; }
        [Display(Name = "Created")]
        public System.DateTime StampCreated { get; set; }
        [Display(Name = "Updated")]
        public System.DateTime StampUpdated { get; set; }
        [Display(Name = "Enabled")]
        public bool IsActive { get; set; }

        public PersonModel()
        {}
        public PersonModel(Person person)
        {
            Id = person.Id;
            FirstName = person.FirstName;
            LastName = person.LastName;
            StampCreated = person.StampCreated;
            StampUpdated = person.StampUpdated;
            IsActive = person.IsActive;
        }

        public static IList<PersonModel> FlattenToThis(IList<Person> people)
        {
            return people.Select(person => new PersonModel(person)).ToList();
        }

    }
}

一緒に移動しています...

@(Html.Kendo().Grid<PersonModel>()
    .Name("PersonGrid")
    .Columns(columns => {
        columns.Bound(b => b.Id).Hidden();
        columns.Bound(b => b.LastName).EditorTemplateName("_TextBox50");
        columns.Bound(b => b.FirstName).EditorTemplateName("_TextBox50");
        columns.Bound(b => b.StampUpdated);
        columns.Bound(b => b.StampCreated);
        columns.Bound(b => b.IsActive).ClientTemplate("<input type='checkbox' ${ IsActive == true ? checked='checked' : ''} disabled />").Width(60);
            columns.Command(cmd => { cmd.Edit(); cmd.Destroy(); }).Width(180);
        })
    .ToolBar(toolbar => toolbar.Create())
    .Pageable()
    .Filterable()
    .Sortable()
    .Selectable()
    .Editable(editable => editable.Mode(GridEditMode.InLine))
    .DataSource(dataSource => dataSource
        .Ajax()
        .Events(events => events.Error("error_handler"))
        .Model(model =>
            {
                model.Id(a => a.Id);
                model.Field(a => a.StampCreated).Editable(false);
                model.Field(a => a.StampUpdated).Editable(false);
                model.Field(a => a.IsActive).DefaultValue(true);
            })
        .Create(create => create.Action("CreatePerson", "People"))
        .Read(read => read.Action("ReadPeople", "People"))
        .Update(update => update.Action("UpdatePerson", "People"))
        .Destroy(destroy => destroy.Action("DestroyPerson", "People"))
        .PageSize(10)
    )
)

これらの_TextBox50は、_TextBox50.cshtmlという名前のEditorTemplatesであり、ビューまたは共有フォルダーのいずれかを基準にしてサブフォルダーに配置する必要があります。フォルダーはEditorTemplatesと呼ばれる必要があります。これはこんな感じ…

@Html.TextBox(string.Empty, string.Empty, new { @class = "k-textbox", @maxlength = "50" })

はい、それだけです。これは単純な例であり、はるかに複雑になる可能性があります。または、最初にそれらを使用する必要はありません。

そして最後に、あなたが本当に探していると思うもの...

public partial class PeopleController : Controller
{
    private readonly IPersonDataProvider _personDataProvider;

    public PeopleController() : this(new PersonDataProvider())
    {}
    public PeopleController(IPersonDataProvider personDataProvider)
    {
        _personDataProvider = personDataProvider;
    }

    public ActionResult Manage()
    {
>>> Left in as teaser, good to apply a special Model to a View to pass goodies ;)
        var model = new PeopleViewModel();
        model.AllQualifications = QualificationModel.FlattenToThis(_qualificationDataProvider.Read());
        return View(model);
    }

    [HttpPost]
    public JsonResult CreatePerson([DataSourceRequest]DataSourceRequest request, Person person)
    {
        if (ModelState.IsValid)
        {
            try
            {
                person = _personDataProvider.Create(person);
            }
            catch (Exception e)
            {
                ModelState.AddModelError(string.Empty, e.InnerException.Message);
            }
        }
        var persons = new List<Person> {person};
        DataSourceResult result = PersonModel.FlattenToThis(persons).ToDataSourceResult(request, ModelState);
        return Json(result, JsonRequestBehavior.AllowGet);
    }

    public JsonResult ReadPeople([DataSourceRequest]DataSourceRequest request)
    {
        var persons = _personDataProvider.Read(false);
        DataSourceResult result = PersonModel.FlattenToThis(persons).ToDataSourceResult(request);
        return Json(result, JsonRequestBehavior.AllowGet);
    }

    [HttpPost]
    public JsonResult UpdatePerson([DataSourceRequest]DataSourceRequest request, Person person)
    {
        if (ModelState.IsValid)
        {
            try
            {
                person = _personDataProvider.Update(person);
            }
            catch (Exception e)
            {
                ModelState.AddModelError(string.Empty, e.InnerException.Message);
            }
        }
        var persons = new List<Person>() {person};
        DataSourceResult result = PersonModel.FlattenToThis(persons).ToDataSourceResult(request, ModelState);
        return Json(result, JsonRequestBehavior.AllowGet);
    }

    [HttpPost]
    public JsonResult DestroyPerson([DataSourceRequest]DataSourceRequest request, Person person)
    {
        if (ModelState.IsValid)
        {
            try
            {
                person = _personDataProvider.Destroy(person);
            }
            catch (Exception e)
            {
                ModelState.AddModelError(string.Empty, "There was an error deleting this record, it may still be in use.");
            }
        }
        var persons = new List<Person>() {person};
        DataSourceResult result = PersonModel.FlattenToThis(persons).ToDataSourceResult(request, ModelState);
        return Json(result, JsonRequestBehavior.AllowGet);
    }
}

この場合、各メソッドはEF Personをパラメーターとして受け取ることに注意してください。PersonModelを使用する方が良いでしょうが、Flattenの反対を表示する必要があります。これらは実質的に同一であるため、これは機能します。モデルが異なる場合、またはクラスファクトリを使用している場合は、少し注意が必要です。

すべてのCRUD操作を意図的に示しました。結果をグリッドに戻さないと、おかしな動作をして、複製が表示されたり、CREATEおよびUPDATEで更新が正しく表示されなかったりします。エラーが発生するModelStateを渡すために、DELETEに戻されます。

そして最後に、想像力に何も残さないように、データプロバイダー...(名前空間宣言は省略されています。)

using System;
using System.Collections.Generic;
using System.Data;
using System.Diagnostics;
using System.Linq;
using Project.Business;

public class PersonDataProvider : ProviderBase, IPersonDataProvider
{
    public Person Create(Person person)
    {
        try
        {
            person.StampCreated = DateTime.Now;
            person.StampUpdated = DateTime.Now;

            Context.People.Attach(person);
            Context.Entry(person).State = EntityState.Added;
            Context.SaveChanges();
            return person;
        }
        catch (Exception e)
        {
            Debug.WriteLine(e.Message);
            throw;
        }
    }

    public IList<Person> Read(bool showAll)
    {
        try
        {
            return (from q in Context.People
                      orderby q.LastName, q.FirstName, q.StampCreated
                      where (q.IsActive == true || showAll)
                      select q).ToList();
        }
        catch (Exception e)
        {
            Debug.WriteLine(e.Message);
            throw;
        }
    }

...

}

InterfaceとProviderBaseの継承に注意してください。これらを作成する必要があります。例を見つけるのに十分単純でなければなりません。

これは多くのコーディングのように思えるかもしれませんが、それを理解したら、コピーして貼り付けてください。

ハッピーコーディング。

于 2013-01-06T01:07:22.173 に答える
0

はい、JsonResultを使用するか、allowgetを指定してJSONを使用してJSONを剣道UIに送り返すことができます。トランスポートでURLを設定し、タイプとしてjsonを指定できます。

最後の質問について、現在ビジュアルツールはありませんが、剣道UIで利用できるヘルパーメソッドはあります

于 2013-01-02T14:27:10.720 に答える