in
Forums
Blogs
Files
Devexpress.Com
ClientCenter
Support Center
DevExpress Channel

Gary's Blog

May 2008 - Posts

  • Groking XAF and XPO #4

    In my previous post we did a little refactoring of our class hierarchy and added the required behaviours to our business objects. In this post we will go ahead and hook up a UI to our hierarchy.

    In this case we will create a windows forms application only for our project, so add a Windows Forms Application Project (from the eXpressApp Framework projects collection) to the solution. We'll call this project DSM (short for Dental Surgery Manager) and the solution should now look as follows:-

    Sol2

    There's a few things we have to do to hook our business objects up to the winforms application, but before we go ahead and do that, there's a small administrative change you have to make if you are using Sql Server Express (as I am). By default the XAF application will persist objects to a database, named the same as the solution, on the local instance Sql Server. If you are running Sql Server Express you have to tell XAF that you want to use this instance for persistence. To do this, build the solution to allow the model designer to work; then, in the DSM.Win project, select WinApplication.cs and select "View Designer" from the context menu. The designer below should now be showing:-

    Designer

    Now select the Sql Connection icon in the top right corner and, in the properties dialog, edit the connection string property so that (local) now reads .\sqlexpress. Whilst we are here in the designer, we'll delete the security icons too, we'll come back and look at security in later posts but, for now, we'll run without it.

    Having done this we can now go ahead and prepare our hierarchy of business objects for inclusion in the XAF project. To do that the first thing we have to do is to decorate the Surgery class with the DefaultClassOptions attribute. This will tell XAF that it is required to add the class to the container on the left hand side of the form, add the class to the "New" menu and create CRUD forms for it and its dependant classes.

    The next thing we have to do is to make the XAF project aware of our business objects, to do that we add a reference to our business objects project from the DSM.Module and DSM.Win projects. Having done this we now select the Module.cs file from the DSM.Module and select "View Designer" from the context menu. As you can see from the image below, the XAF project is now aware of our business objects:-

    BusObjects

    Now the last thing we have to do is to tell XAF that we want it to use those objects, we do this be selecting the objects and pressing the SPACE key, the object will embolden to signify that it will be used in the solution, like so:-

    BusObjects2 

    Now we can hit F5 and test out our UI:-

    Form

    Go ahead and play around with the UI, create a Surgery and add Patients and Dentists etc. The layout of the form fields is a little erratic but we'll sort that out in future posts, but for now, satisfy yourself that the UI works as advertised.

    That wraps it up for this post where we took an existing business object hierarchy and hooked it up to an XAF winforms application. In the next post we'll look at customising the UI, hope to see you then.

    Technorati tags: , ,
  • Groking XAF and XPO #3

    In my previous post in this series we covered creating a hierarchy of business objects, persisting them using XPO and then creating a test to ensure that we had wired up the persistence mechanism properly. In this post we will take our object hierarchy to the next stage, by adding in the required bahaviours, carrying out some necessary refactoring, and adding to our test project.

    So let's go ahead and add the behaviours we need to our hierarchy. The required behaviours are detailed in the following use case diagram:-

    UseCase

    As you can see, a Receptionist makes appointments and reminds a Patient of appointments whilst a PracticingEmployee updates the Patient's notes. Wait a minute? PracticingEmployee, what's that, there's not one of those in our hierarchy? No there wasn't. When we were laying out the properties of each object we shook out the hierarchy that we have. However, now when we come to add the object behaviours, we realise that whilst a Dentist and a Hygienist will update Patient notes, a receptionist will not, therefore we need a new abstract object to describe a practicing employee; we also need to add a PatientNotes object, which will maintain a collection of objects of type Note. After we add these new objects, our hierarchy will look like this:-

    UML2

    Now let's add the code to make an appointment:-

    /// <summary>
    /// Given a Patient, a PracticingEmployee and a DateTime, 
    /// create and return an Appointment
    /// </summary>
    /// <param name="patient">The Patient the Appointment is for</param>
    /// <param name="practicingEmployee">The PracticingEmployee that the 
    /// Patient will see</param>
    /// <param name="timeOfAppointment">The time of the appointment</param>
    /// <param name="session">The current UnitOfWork</param>
    /// <returns>An Appointment object</returns>
    public Appointment MakeAppointment(Patient patient, 
        PracticingEmployee practicingEmployee,
        DateTime timeOfAppointment,
        Session session)
    {
        Appointment appointment = new Appointment(session);
        appointment.Patient = patient;
        appointment.PracticingEmployee = practicingEmployee;
        appointment.TimeOfAppointment = timeOfAppointment;
        return appointment;
    }

    and the code to remind a Patient of an Appointment:-

    /// <summary>
    /// Send an email reminding a Patient of their appointment
    /// </summary>
    /// <param name="appointment">The Appointment</param>
    /// <returns></returns>
    public bool RemindPatientOfAppointment(Appointment appointment)
    {
        string message = String.Format("Dear {0} this is an email to " +
            "remind you that you have an appointment with {1} {2} on {3}" +
            "at {4}",appointment.Patient.FirstName,
            appointment.PracticingEmployee.FirstName,
            appointment.PracticingEmployee.LastName,
            appointment.TimeOfAppointment.Date.ToLongDateString(),
            appointment.TimeOfAppointment.TimeOfDay.ToString());
    
        //GS - Simulate a sucessful email send
        Console.WriteLine(message);
        Console.ReadLine();
        return true;
    }

    followed by the code to update the Patient's notes:-

    /// <summary>
    /// Add a new note to the Patients notes
    /// </summary>
    /// <param name="patient">The Patient</param>
    /// <param name="note">The text of the note to add</param>
    /// <param name="session">The current UnitOfWork</param>
    public void UpdatePatientsNotes(Patient patient, String note, 
        Session session)
    {
        Note newNote = new Note(session);
        newNote.UpdateNote = note;
        newNote.UpdateDate = DateTime.Now;
        patient.PatientNote.Notes.Add(newNote);
    }

    Now we must add tests for making an appointment and updating a Patient's notes:-

    [TestMethod()]
    public void MakeAppointmentTest()
    {
        //GS - When shall we make the appointment for?
        DateTime timeOfAppointment = DateTime.Now;
    
        //GS - Ask a Receptionst to make an Appointment and persist it
        using (var uow = new UnitOfWork())
        {
            Receptionist receptionist = new Receptionist(uow); 
            Patient patient = new Patient(uow);
            Dentist dentist = new Dentist(uow);
            receptionist.MakeAppointment(patient, dentist, 
                timeOfAppointment, uow);
    
            uow.CommitChanges();
        }
    
        //GS - Verify an appointment was persisted.
        using (var uow = new UnitOfWork())
        {
            var criteria = new BinaryOperator("TimeOfAppointment", timeOfAppointment);
            var appointment = uow.FindObject<Appointment>(criteria);
            Assert.IsNotNull(appointment);
        }
    }
    [TestMethod()]
    public void UpdatePatientsNotesTest()
    {
        //GS - What text shall we add to the Patients notes?
        string noteText = "The patient was seen";
    
        //GS - Add the Note to the Patients notes and persist it
        using (var uow = new UnitOfWork())
        {
            Dentist dentist = new Dentist(uow);
            Patient patient = new Patient(uow);
            PatientNote patientNote = new PatientNote(uow);
            patient.PatientNote = patientNote;
            dentist.UpdatePatientsNotes(patient, noteText, uow);
    
            uow.CommitChanges();
        }
    
        //GS - Veryify the note was persisted
        using (var uow = new UnitOfWork())
        {
            var criteria = new BinaryOperator("UpdateNote", noteText);
            var note = uow.FindObject<Note>(criteria);
            Assert.IsNotNull(note);
        }
    }

    And that's it for this post. In this post we extended our object hierarchy by adding in our object behaviours, we also did a little refactoring to allow for new objects that came to light whilst we were adding our object behaviours and we extended our tests to ensure that our behaviours worked as advertised. Now that we have completed work on our object hierarchy, in the next post, we'll add in the XAF solution to our solution and start work on creating our web and winform applications. Hope to see you next time!

    Technorati tags: ,

  • Do you use XAF? Going to TechEd? Then we Want to Hear from You!

    As Julian mentioned in his blog post, the eXpressApp Framework has been nominated for a Best of TechEd award. Obviously we really appreciate this nomination and we look forward to spending time with all of our customers at TechEd demonstrating XAF. However, we want to go further, if you're a user of XAF then we'd like to give your application a bit of publicity too; we'd like to sit down and get you and your product on video at TechEd. If you are interested then drop me an email (garys@devexpress.com) or stop by the Developer Express booth anytime. Hope to see you there!

  • Groking XAF and XPO #2

     Well as you can see I’m not highly imaginative when it comes to blog post titles but I thought I’d continue with the Stranger in a Strange Land theme. If you’ve read my last blog posting on the subject you’ll know I’m busy learning about XAF and XPO for my new role at Developer Express and if you are following along, by now you should have read the documentation and watched the videos that I pointed to in that post.

    So, what now? Well I don’t know about you, but I find the easiest way to learn about a programming tool or framework is to write a small application using it, so that’s what I’m going to start to do in this post. Specifically, I’m going to start to build an application to manage a hypothetical dental surgery.

    The development of every application has to start somewhere and with XAF based applications that usually (but not always) means starting by working out the hierarchy of objects in your solution domain, so our hierarchy is going to look like this:-

    UML Diagram

    For those of you who don’t speak UML, I’ll talk you through the diagram. A dental Surgery has one or more people associated with it, each Person is either an Employee or a Patient, of those who are employees, they are either a Dentist, a Receptionist or a Hygienist. Patients have one or more appointments with a Dentist or a Hygienist.

    Having decided on our hierarchy of objects, let’s go ahead and build it in Visual Studio. Create a new solution and add a class library project and create the hierarchy of objects by carrying out the steps shown in this video, remembering to add the one-to-many relationship between Surgery and People as per the documentation here. Don’t worry if you mess it up, we’ll fix it as we go. When you have finished your project will look something like this:-

    Sol1

    Having done that, let’s test our application. Add a new unit test to the solution (I’ll be using the built in VS tests but you can use your favourite unit testing suite) and write a test to create a new Surgery and a Dentist to work in that Surgery. In your test initialiser you need to write the following code to tell XPO where to put the database (we’ll be using the default Access implementation for the moment) and to build the schema if it does not already exist:-

    [ClassInitialize()]
    public static void MyClassInitialize(TestContext testContext) 
    {
        //GS - Create a sensible location for the database
        string path = @"C:\databases\XPODemo\XPOLayer.mdb";
    
        //GS - If it exists, delete the database before the tests begin
        if (File.Exists(path))
        {
            File.Delete(path);
        }
        
        //GS - Set the default session to null
        XpoDefault.Session = null;
        
        //GS - Explicitly set the default data layer
        XpoDefault.DataLayer =
            XpoDefault.GetDataLayer(
                AccessConnectionProvider.GetConnectionString(path),
                    AutoCreateOption.DatabaseAndSchema);
    }

    Then add the following test to add a new Surgery object:-

    [TestMethod]
    public void AddSurgeryAndDentist()
    {
        using (var uow = new UnitOfWork())
        {
            //GS - Create a new Surgery
            var surgery = new Surgery(uow);
            surgery.Name = "Test Name";
            surgery.Address1 = "27, Haggis Street";
            surgery.Address2 = "Dundee";
            surgery.Address3 = "Scotland";
            surgery.Address4 = "UK";
            surgery.Postcode = "DD7 7YG";
    
            //GS - Create a Dentist to work at the Surgery
            var dentist = new Dentist(uow);
            dentist.FirstName = "Gary";
            dentist.LastName = "Short";
            dentist.Address1 = "Address1";
            dentist.Address2 = "Address2";
            dentist.Address3 = "Address3";
            dentist.Address4 = "Address4";
            dentist.Postcode = "DD3 8JK";
            dentist.Email = "email@domain.com";
            dentist.Hours = 37;
            dentist.PayNumber = "RA 23445";
            dentist.Salary = 42000.00f;
    
            //GS - State that the Dentist works at the Surgery
            surgery.People.Add(dentist);
    
            //GS - Persit the object
            uow.CommitChanges();
        }
    
        using (var uow = new UnitOfWork())
        {
            //GS - Test that the Surgery object was persisted
            var Criteria = new BinaryOperator("Name", "Test Name");
            var surgery = uow.FindObject<Surgery>(Criteria);
            Assert.IsNotNull(surgery);
        }
    }

    Well, I think that will do us for this post. In this post we devised a hierarchy of solution domain objects, then we implemented those objects using XPO as the persistence mechanism and finally we wrote tests to validate that we could persist our objects properly. In the next post, we’ll extend our solution to add different behaviours to our objects; we’ll also extend our test project to validate that behaviour. Hope to see you next time!

    Technorati tags: ,

  • Developer Day Scotland and community Feedback

    Well this weekend I was speaking at the Developer Day Scotland conference in sunny (for a change) Glasgow. It was a great conference with a lot of great speakers including Oliver, who was also there.

    Whilst there, I got chatting to a guy from Redgate, they're a big user of our components and love them, but they don't think they're perfect and he had some suggestions for improvements that they wanted to talk to me about. So, to cut a long story short, I'm going to make arrangements to travel down to their company and spend some time with their devs, who are actually using our products in the wild, and see what suggestions they've come up with; I'll then pass those suggestions on to the product managers here at DX.

    If you have issues with, or suggestions for, our products, then please don't hesitate to pass them on to me via comments to my blog posts, email, follow me on Twitter, or by far the best, is face to face. I publish my calendar online, so check out where I'm going to be, and if we're going to be at the same events then come along and say hi and put forward your suggestions, just like the Redgate guys did.

    To that end, I'll be at the MSDN Roadshow in Glasgow tomorrow, so if you're going, don't forget to introduce yourself and let me know what you think of our products. 

  • Stranger in a Strange Land

    Much like Valentine Michael Smith, when you first come to XAF it can be a daunting experience, "how am I ever going to grok all this?", you may ask yourself. I asked myself the same question not long ago when I joined the company (predominately to evangelise about XAF). Luckily there are some great resources on the DX site to help you get started. There is documentation on XAF here and on XPO here. There are also some great video tutorials here.

    Also, you can follow a short series of blog posts I'll be doing (this being the first) where I chart my journey aong the road to "groking" the framework. So, if you want some company, we can be strangers in a strange land together. :-)

  • Developer Day Ireland Conference

    This Saturday (May 3) Oliver and I will be at the Developer Day conference in Ireland; as always, if you are a Developer Express customer - or a potential customer, please stop us and say hello and let us know what you think about our products and we'll feedback your comments to the product teams here. Look forward to seeing you there!

Copyright © 1998-2008 Developer Express Inc.
ALL RIGHTS RESERVED