четверг, июля 29, 2010

Простейшее приложение с использованием Silverlight / RIA / POCO

В данном посте своего хай-тек блога я-бы хотел показать вам как создать простейшее приложение на Silverlight с использованием RIA/POCO. Этот пример будет настолько прост на сколько это возможно. Для этого будем рассматривать только вариант с чтением данных. Про обновление поговорим в следующий раз.
Итак нам понадобится

  1. Скачать и установить Silverlight 4.0 и WCF RIA Services 1.0
  2. Скачать Silverligth Toolkit
  3. Создать компонент бизнес слоя
Когда вы приступаете к созданию приложения Silverlight/RIA у вас уже обычно есть слой бизнес компонент которые вы будете использовать. В этом примере вы будем использовать простейший класс Customer.
Создайте проект стандартной библиотеки классов (Class Library) и добавьте туда следующий код:














using System.Collections.Generic;
namespace ACM.BLCSharp
{
    ///
    /// Manages a customer
    ///

    public class Customer
    {
        public int CustomerId { get; set; }
        public string LastName { get; set; }
        public string FirstName { get; set; }
        public string EmailAddress { get; set; }
        ///
        /// Retrieves a list of customers.
        ///

        ///
        ///
        /// In a "real" application, this code would
        /// call a data access component that retrieves
        /// the data from a database.
        ///

        public List Retrieve()
        {
            List custList = new List
                    {new Customer()
                          { CustomerId = 1,
                            FirstName="Bilbo",
                            LastName = "Baggins",
                            EmailAddress = "bb@hob.me"},
                    new Customer()
                          { CustomerId = 2,
                            FirstName="Frodo",
                            LastName = "Baggins",
                            EmailAddress = "fb@hob.me"},
                    new Customer()
                          { CustomerId = 3,
                            FirstName="Samwise",
                            LastName = "Gamgee",
                            EmailAddress = "sg@hob.me"},
                    new Customer()
                          { CustomerId = 4,
                            FirstName="Rosie",
                            LastName = "Cotton",
                            EmailAddress = "rc@hob.me"}};
            return custList;
        }
    }
}
Обычно я создаю пару классов: Customer - для представления единичной записи и Customers для операций над списками. Для упрощения в этом примере этим занимается один класс. Как вы заметили данный класс для упрощения не использует слой доступа к данным.


Шаг первый: добавить атрибуты на объекты предназначенные для Silverlight
Существуют несколько атрибутов которыми вы можете снабдить свой бизнес объект для улучшения их совместной работы с Silverlight. Но о единственным необходимым атрибутом для работы с WCF RIA является атрибут Key который, будучи примененным к свойству объекта, задает это свойство как уникальный ключ объекта. В нашем примере это свойство CustomerId.

using System.ComponentModel.DataAnnotations;
[Key()]
public int CustomerId { get; set; }

Шаг второй: создание проекта Silverlight

  1. Щелкните правой кнопкой на решении и выберите Add > New Project
  2. Выберите Silverlight > Silverlight Application (Будте внимательны и добавляйте проект для своего языка)
  3. Поставить галочку Enable WCF RIA Services


Когда вы добавляете проект Silverligth то Visual Studio создаст и проект Silverligth и проект ASP.NET. Второй важен из-за двух аспектов:

  • Он содержит код для запуска Silverligth приложения
  • Он предоставляет сервис WCF для общения между вашим Silverligth приложением и вашими бизнес объектами.
Если же у вас уже есть созданный проект Silverlight вы все еще можете включить WCF RIA в настройках проекта:




Шаг третий: добавьте ссылку на Бизнес Компоненты в проект ASP.NET приложения
Выберите свое ASP.NET приложение затем Add Reference и там свое проект с бизнес объектами. Таким образом мы разрешаем ASP.NET проекту доступ к нашему бизнес слою.

Шаг четвертый:Добавить Domain Service Class
Добавьте Domain Service Class а в приложение ASP.NET (он вызывает методы вашего бизнес слоя). Данный класс должен быть размещен а ASP.NET приложении, а не в приложении Silverlight т.к. последнее исполняется в браузере клиента а ASP.NET приложение выполняется на сервере где может получить доступ в вашим бизнес компонентам.
Чтобы добавить Domain Class Service щелкните правой кнопкой мышки на ASP.NET приложении и выберите Add > New Item, и там выберите шаблон Domain Service Class.
В этом месте у нас сильное различие с примером от Entity Framework. Если-бы мы использовали данный фреймворк то тут был-бы список сущностей. Если-же ,как в нашем случае, использовать  свои бизнес объекты, то тут будет пусто. Все нормально. Просто нажмите ОК.
Так-как мы используем свои бизнес объекты - Visual Studio будет наслежовать наш класс от DomainService. Если-бы мы использовали Entity Framework класс наследовался-бы от LinqToEntitiesDomainService.
В большинстве случаев вы будете создавать Domain Service Class для каждого из своих бизнес объектов.


Шаг пятый: Добавить метод запроса данных к Domain Service Class
Метод запроса должен вызывать метод Retrive бизнес-объекта.

namespace ACM.SilverlightCSharp.Web
{
    using System.Collections.Generic;
    using System.ServiceModel.DomainServices.Hosting;
    using System.ServiceModel.DomainServices.Server;
    using ACM.BLCSharp;
    [EnableClientAccess()]
    public class CustomerDomainService : DomainService
    {
        public IEnumerable GetCustomers()
        {
            Customer cust = new Customer();
            return cust.Retrieve();
        }

    }
}


Несколько замечаний по поводу метода GetCustomers

  • Должен быть методом а не свойством
  • Должен возвращать одно из следующих:





    • Единичную сущность
    • IEnumerable где T - единичная сущность
    • IQueryable где T - единичная сущность
  • Может иметь любые параметры
  • Может иметь любое имя
  • Может (но не обязан) содержать атрибут Query что-бы задать метода как запрос
WCF RIA Services распознает метод как запрос благодаря типу возвращаемого значения. Таким образом метод должен иметь один из трех типов о которых говорилось ранее.
Если вы построите проект в данный момент и посмотрите все файлы то в папке Generated_Code  Silverlight проекта вы увидите .g.csc файлы. Это сгенерированный код для:
  • Классы сущностей (Customers в нашем примере) - генерируется из объектов бизнес-слоя и включает в себя все свойства сущности.
  • Класс Domain Context  (CustomersDomainContext в нашем примере) - через инфраструктуру WCF вызывает методы Domain Service Class нашего ASP.NET проекта
В добавок ко всему сгенерированный код содержит контракт сервиса для Domain Service Class в ASP.NET приложении

Шаг шестой: Создание UI
И опять для упрощения примера будем использовать грид для отображения данных.
  1. Откройте дизайнер файла MainPage.xaml (двойной клик на файле)
  2. Открыть список Data Sources ( Data > Show Data Sources )
Visual Studio автоматически добавила определенные domain context clas в список источников данных
Просто перетащите источник данных Customer на панель дизайнера и Visual Studio сделает все остальное.

Шаг шестой: Запуск
Если запустить приложение вы должны увидеть:
Это работает из-за того что когда вы переносите источник данных на страницу в дизайнере Visual Studio создает контролы DomainDataSource и DataGrid. На DomainDataSouce устанавливается свойство QueryName в "GetCustomersQuery" и на DataGrid свойство ItemsSource устанавливается на DomainDataSource
Сгенерированный код прибавляет Query в конец имени вашего метода. И именно в таком виде (GetCustomersQuery) его надо вызывать из UI у domain context class. Этот метод вызовет метод GetCustomers нашего Domain Service Class, который в свою очередь вызовет метод Retrive нашего бизнес-объекта.
Вот как это примерно выглядит:


Надеюсь вы помните что все усилия по создвнию сайта могут не окупиться. Что-бы такого не произошло я предпочитаю доверять продвижение сайта проффесионлам

2 комментария:

  1. Анонимный17:50

    Я НАПРИМЕР ДЕЛАЛ ВСЕ ЧТО ЗДЕСЬ НАПИСАНО И ЗАСТРЯЛ НА 6 ПУНКТЕ - ТАМ ГДЕ З СИТОЧНИКОВ ДАННЫХ ДОБАВЛЯТЬ ГРИД НА ФОРМУ - У МЕНЯ В ЕТИХ ИСТОЧНИКАХ ПУСТО И МАЯЧИТЬ ОШИБКА

    Ошибка 1 The entity 'Object' in DomainService 'CustomerDomainService' does not have a key defined. Entities exposed by DomainService operations must have at least one public property marked with the KeyAttribute. ACM.SilverlightCSharp
    Я К ВСЕМУ В <> ПИСАЛ OBJECT

    ОтветитьУдалить
  2. Судя по сообщению об ошибке вы забыли пометить ключ объекта атрибутом [Key()] :
    Прмер
    [Key()]
    public int CustomerId { get; set; }

    ОтветитьУдалить