INFS7204 – Services-Oriented Architectures

This subject covered the fundamentals of the development paradigm services-oriented architecture with practical assignments written in C#. The 4 assignments involved building simple web applications using .Net 4 – ASP.net, C# web services, and HTML/JavaScript.

Practical 1 – Calculator

This first assignment was a simple introduction to web services and ASP.net. The task was to build a simple calculator web form. For extra credit, also build a binary number converter and a feature to count (literally) the 0s and 1s in the resultant binary number.

using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.UI;
using System.Web.UI.WebControls;

public partial class _Default : Page
{
    public float result_base_10;
    public string result_base_2;

    protected void Page_Load(object sender, EventArgs e)
    {

    }

    protected void calc_Click(object sender, EventArgs e)
    {
        string operation = Operation.Text;

        if (InputA.Text.Length > 0 && InputB.Text.Length > 0)
        {
            switch (operation)
            {
                case "+":
                    result_base_10 = float.Parse(InputA.Text) + float.Parse(InputB.Text);
                    break;
                case "-":
                    result_base_10 = float.Parse(InputA.Text) - float.Parse(InputB.Text);
                    break;
                case "*":
                    result_base_10 = float.Parse(InputA.Text) * float.Parse(InputB.Text);
                    break;
                case "/":
                    result_base_10 = float.Parse(InputA.Text) / float.Parse(InputB.Text);
                    break;
            }
        }

        update_base_10();
        update_base_2();
    }
    
    protected void update_base_10()
    {
        Base10.Text = result_base_10.ToString();
    }

    protected void update_base_2()
    {
        string base_2_result = result_base_10.ToString();
        result_base_2 = Convert.ToString((int) result_base_10, 2);
        
        Base2.Text = result_base_2;
    }


    protected void count_Click(object sender, EventArgs e)
    {
        int countOf0 = 0;
        int countOf1 = 0;

        string base2 = Base2.Text;
        
        for (int i = 0; i <= base2.Length - 1; i++)
        {
            if (base2[i] == '0') { countOf0++; }
            if (base2[i] == '1') { countOf1++; }
        }

        count0.Text = countOf0.ToString();
        count1.Text = countOf1.ToString();
        

    }
}

Assignment 2 – Post Code Finder and Zodiac converter

In this assignment we were supplied with a text file of a selection of Brisbane postcodes/Suburbs and which we needed to read in, process and return the postcode given the selection of a dropdown menu. In the second part we needed to provide a converter between a day/month and its corresponding zodiac sign.

Postcode Finder

The Postcode Finder part of this assignment required us to use an asp:updatepanel object and to prove its use by printing the System.DateTime.Now outside the updatepanel.

 [WebMethod]
        public string PostCodeFinder(string suburb)
        {
            string line;
            string filename = Server.MapPath("~") + "/Postcodes.txt";
            System.IO.StreamReader file = new System.IO.StreamReader(filename);
            Dictionary postcodes = new Dictionary();
            while ((line = file.ReadLine()) != null) {
                string[] subPC = line.Split(',');
                postcodes.Add(subPC[0], subPC[1]);
            }
            return postcodes[suburb];
        }

        [WebMethod]
        public List SuburbList()
        {
            string line;
            string fname = Server.MapPath("~") + "/Postcodes.txt";
            System.IO.StreamReader file = new System.IO.StreamReader(fname);
            List suburbs = new List();
            int i = 0;
            while ((line = file.ReadLine()) != null)
            {
                int sepPos = line.IndexOf(",");
                suburbs.Add(line.Substring(0, sepPos));
                i++;
            }
            return suburbs;
        }

Zodiac Converter

For the zodiac converter, I used a simple case statement to return the dates given a zodiac. The requirements had us enter the day and month as separate strings in the web form. To return the zodiac given the day/month I simply concatenated them and compared them as a number in the form “mmdd”.

[WebMethod]
        public string ToZodiac(string month, string ordinal)
        {
            string combo = string.Concat(month, ordinal);
            if (combo.Length != 0) {
                int date = Convert.ToInt16(combo);

                if (int.Parse(month) > 12) { return "Wrong Input Date"; }
                if (int.Parse(ordinal) > 31) { return "Wrong Input Date"; }
                int[] monthsMoreThan31 = {1, 3, 5, 7, 8, 10, 12 };
                if (monthsMoreThan31.Contains(int.Parse(month)) && int.Parse(ordinal) > 31) { return "Wrong Input Date"; }

                int[] monthsMoreThan30 = { 4, 6, 9, 11 };
                if (monthsMoreThan30.Contains(int.Parse(month)) && int.Parse(ordinal) > 30) { return "Wrong Input Date"; }

                if (int.Parse(month) == 2 && int.Parse(ordinal) > 28) { return "Wrong Input Date"; }

                if (date >= 0321 && date < 0420) { return "Aries"; }
                                  ...
                if (date >= 1123 && date < 1222) { return "Sagittarius"; }
                if (date >= 1223 || date < 0120) { return "Capricorn"; }
                if (date >= 0120 && date < 0219) { return "Aquarius"; }
                if (date >= 0219 && date < 0321) { return "Pisces"; }

                if (int.Parse(month) > 12) { return "Wrong Input Date"; }
                if (int.Parse(ordinal) > 31) { return "Wrong Input Date"; }
            }
            return "Not Found";
        }

Assignment 3 – Bookstore Application

This task was to create a simple (and mock) book store application – add, search, delete, and purchase books. We only needed to save to a text file (CSV) as database use was beyond the scope of the course.

I’ll only show code samples of the more interesting features.

public List SearchBook(string field, string value)
        {
            var matchingBooks = new List();

            foreach (var book in ReadBooks())
            { 
                if (field == "Name" && book.name.ToLower().Contains(value.ToLower()))
                { 
                    matchingBooks.Add(book);
                }
                if (field == "Author" && book.author.ToLower().Contains(value.ToLower()))
                {
                    matchingBooks.Add(book);
                }
                if (field == "ID" && book.ID == value)
                {
                    matchingBooks.Add(book);
                }

                //exception handling extra code for year inputs - we'll use 0 if the year isn't an int
                int Year = 0;
                bool validYear = int.TryParse(value, out Year);
                if (validYear) { Year = Convert.ToInt32(value); }
                if (field == "Year" && book.year == Year)
                {
                    matchingBooks.Add(book);
                }
            }

            return matchingBooks;
        }
// WriteBooks writes the list of books to the file in CSV format.
        private bool WriteBooks(List books)
        {
            try
            {
                using (TextWriter file = new StreamWriter(fname))
                {
                    foreach (var book in books)
                    {//$"{book.ID},{book.name},{book.author},{book.year},{book.price.ToString("C")},{book.stock}");
                        file.WriteLine(String.Format("{0},{1},{2},{3},{4},{5}", 
                            book.ID, 
                            book.name, 
                            book.author, 
                            book.year, 
                            book.price.ToString("C"),
                            book.stock));
                    }
                }
                return true;  
            } 
            catch(IOException)
            {
                return false;
            }
        }

For purchasing the books, we didn’t need to actually decrease stock or money, since it was just an exercise in creating web services, rather than actually building a book store.

public BookPurchaseResponse PurchaseBooks(BookPurchaseInfo purchase)
        {
            //read the purchase items and gather the stocks and prices
            //return various values for
            BookPurchaseResponse purchaseResponse = new BookPurchaseResponse();
            ServiceReference1.BookServiceClient books = new ServiceReference1.BookServiceClient();
            float totalBookPurchaseCost = 0;
            var bookList = books.GetAllBooks();
            Dictionary booksWithIndex = new Dictionary();
            //let's loop over the bookList and add the Num
            int i = 0;
            foreach (var book in bookList)
            {
                i++;
                booksWithIndex[i] = book;
            };
            //now let's check the items to buy
            foreach (var item in purchase.items)
            {
                //check the stock first
                try
                {
                    if (booksWithIndex[item.Key].stock >= item.Value)
                    {
                        //enough of this book so add the cost to total
                        totalBookPurchaseCost = totalBookPurchaseCost + (item.Value * booksWithIndex[item.Key].price);
                    }
                    else
                    {
                        //not enough stock so return that
                        purchaseResponse.response = "Not enough stock";
                        purchaseResponse.result = false;
                        break;
                    }
                    if (purchase.budget < totalBookPurchaseCost)
                    {
                        //not enough money so we should stop checking anyway
                        purchaseResponse.response = "Not enough money";
                        purchaseResponse.result = false;
                        break;
                    }
                    else //never failed so it must be fine
                    {
                        float moneyLeft = purchase.budget - totalBookPurchaseCost;
                        purchaseResponse.response = moneyLeft.ToString("C"); //convert it to a string with currency formatting
                        purchaseResponse.result = true;
                        
                        
                    }
                }
                //catch { }
                catch (KeyNotFoundException)
                {
                    //entered a Num that's not in the bookList
                    purchaseResponse.response = "Not enough stock";
                    purchaseResponse.result = false;
                    break;
                }
            }
            return purchaseResponse;
        }
    }