BusinessLogic.web - a .NET business logic wrapper for Javascript

Friday, April 14, 2006

This is a sample of BusinessLogic.web - A javascript business logic wrapper for ASP.NET.

BusinessLogic.web is Part of dotWeb - A .NET Business Framework for the web under development by beaconware ApS.

The aim of this project is to aid the developer in the proces of writing business logic for the right tier - that is the server - and in a compiled language. Most people can agree on that. This wrapper simplifies the proces of making a business entity available on the client even though it really lives on the server.

BusinessLogic.web concerns itself with BUSINESS ONLY and it's very good at just that.

A very cool thing about this tool is, that you don't have to write web services anymore! Play with it!!

Business Classes

This is the Person class with the business logic layer.

It inherits from dotWeb.Core.Business.Entity, but that is just my own preference, the Entity class is optional, but make sure your business class supports IJsonFormattable, if you don't inherit from the Entity class!

Remember to put [Wrap] attributes on your class and on your public methods to make them available on the client. On the client side public properties will be wrapped like standard javascript properties, but if you want the getter or setter of a property available, like "set_PhoneNumber(value)" then you have to wrap them by specifying the [Wrap] attribute on the "set" symbol.

using System.Data.SqlTypes;
using dotWeb.Core.Scripting;
using dotWeb.Core.Business;

namespace MyCompany.Business.Logic {
  [Wrap]
  public class Person : Entity {
    protected SqlInt32 iId = SqlInt32.Null;
    protected SqlString sName = SqlString.Null;
    protected SqlString sPhoneNumber = SqlString.Null;

    public override SqlInt32 Id {
      get { return iId; }
      set { iId = value; }
    }

    public SqlString Name {
      get { return sName; }
      set { sName = value; }
    }

    public SqlString PhoneNumber {
      get { return sPhoneNumber; }
      [Wrap]
      set { 
        sPhoneNumber = value; 
      }
    }

    [Wrap]
    public void SetProperties(SqlString sName,
      SqlString PhoneNumber) {
      Name = sName;
      PhoneNumber = sPhoneNumber;
    }

    [Wrap]
    public void Save() {
      MyCompany.Data.SavePerson(this);
    }

    public Person(SqlInt32 iId) {
      Id = iId;
      MyCompany.Data.LoadPerson(this);
    }

    public Person() {
    }
  }
}
    

Data layer

This i the data layer. For simplicity the data layer below uses the web server memory instead of a database. For any real life use, implement the database operations.

using System.Collections.Generic;
using System.Data.SqlTypes;
using System;
using MyCompany.Business.Logic;
using dotWeb.Core.Scripting;

namespace MyCompany {
  [Wrap]
  public class Data {
    protected static Dictionary<Int32, Person> 
      oPersonTable = null;

    [Wrap]
    public static Dictionary<Int32, Person> PersonTable {
      get {
        if (oPersonTable == null) {
          //Implement your database loader here ...
          oPersonTable = new Dictionary<Int32, Person>();

          Person oPerson = new Person();
          oPerson.Id = 1;
          oPerson.Name = "Federico Ferris";
          oPerson.PhoneNumber = "555-6519845";
          oPersonTable[oPerson.Id.Value] = oPerson;

          oPerson = new Person();
          oPerson = new MyCompany.Business.Logic.Person();
          oPerson.Id = 2;
          oPerson.Name = "Kenneth Williamson";
          oPerson.PhoneNumber = "555-9877521";
          oPersonTable[oPerson.Id.Value] = oPerson;

          oPerson = new Person();
          oPerson.Id = 3;
          oPerson.Name = "Jess Nash";
          oPerson.PhoneNumber = "555-7498888";
          oPersonTable[oPerson.Id.Value] = oPerson;
        }
        return oPersonTable;
      }
      [Wrap]
      set {
        oPersonTable = value;
      }
    }

    public static void LoadPerson(
      MyCompany.Business.Logic.Person oPerson) {
      if (oPerson.Id.IsNull) {
        oPerson.Id = SqlInt32.Null;
        oPerson.Name = SqlString.Null;
        oPerson.PhoneNumber = SqlString.Null;
      }
      else {
        if (PersonTable.ContainsKey(oPerson.Id.Value)) {
          oPerson.Name = PersonTable[oPerson.Id.Value].Name;
          oPerson.PhoneNumber = 
            PersonTable[oPerson.Id.Value].PhoneNumber;
        }
      }
    }

    public static void SavePerson(
      MyCompany.Business.Logic.Person oPerson) {
      if (!oPerson.Id.IsNull) {
        //Implement your database updater here ...

        if (PersonTable.ContainsKey(oPerson.Id.Value)) {
          PersonTable[oPerson.Id.Value].Name = oPerson.Name;
          PersonTable[oPerson.Id.Value].PhoneNumber = 
            oPerson.PhoneNumber;
        }
        else {
          PersonTable[oPerson.Id.Value] = new Person();
          PersonTable[oPerson.Id.Value].Id = oPerson.Id;
          PersonTable[oPerson.Id.Value].Name = oPerson.Name;
          PersonTable[oPerson.Id.Value].PhoneNumber = 
            oPerson.PhoneNumber;
        }
      }
    }

    public static void DeletePerson(
      MyCompany.Business.Logic.Person oPerson) {
      if (!oPerson.Id.IsNull) {
        //Implement your database deleter here ...

        if (PersonTable.ContainsKey(oPerson.Id.Value)) {
          PersonTable.Remove(oPerson.Id.Value);
        }
      }
    }
  }
}
    

Javascript

Calling a static property setter on MyCompany.Data

    
<script language=Jscript>

  MyCompany.Data.set_PersonTable(null);
  alert("Person table is now reset.");

</script>
    

Reading Person properties.

   
<script language=Jscript>

  var oPerson = new MyCompany.Business.Logic.Person(1);
  alert("Person with Id 1 has the following name: "
   + oPerson.Name);

  var oPerson = new MyCompany.Business.Logic.Person(2);
  alert("Person with Id 2 has the following phone number: " 
    + oPerson.PhoneNumber);

  var oPerson = new MyCompany.Business.Logic.Person(3);
  alert("Person with Id 3 has the following name: "
    + oPerson.Name);

</script>
    

Updating a Persons properties.

      
<script language=Jscript>

  var oPerson = new MyCompany.Business.Logic.Person(1);
  alert("Person with Id 1 has the following name: " 
    + oPerson.Name + " and phone number: " 
    + oPerson.PhoneNumber);
  
  oPerson.Name = "Brandon Carpenter";
  oPerson.PhoneNumber = "555-9872112";

  alert("Invoking method Person.Save()");
  oPerson.Save();
  
  var oPerson = new MyCompany.Business.Logic.Person(1);
  alert("Person with Id 1 now has the following name: " 
    + oPerson.Name + " and phone number: " 
    + oPerson.PhoneNumber);

</script>
    

Invoking Person methods.

<script language=Jscript>

  var oPerson = new MyCompany.Business.Logic.Person(2);

  alert("Person with Id 2 now has the following name: " 
    + oPerson.Name
    + " and phone number: " + oPerson.PhoneNumber);

  alert("Now invoking method " 
    + "Person.SetProperties('Russel Yeager', '555-987445')");
  oPerson.SetProperties('Russel Yeager', '555-987445');

  alert("Person with Id 2 now has the following name: "
    + oPerson.Name + " and phone number: " 
    + oPerson.PhoneNumber);
</script>
    

3 Comments:

Anonymous Anonymous said...

very interesting.

once a "wrapper generator" exists for data tables, this could be the best way to implement the idea of separating client side code from server side code.

9:03 AM  
Blogger Troels Wittrup said...

And it does. I have written a code generator with object relation mapping (ORM) and all the works. It supports the [Wrap] attribute, which means that the business entities and methods are available both server-side and client-side.

I just haven't come around to publish the code yet :)

Write me if you are interested in a peek at the project.

3:09 AM  
Blogger zang said...

Nice Post
-------------
article rewrite

4:27 AM  

Post a Comment

<< Home