Ben Smithurst
Final Year Project  
next up previous contents
Next: Implementation Up: A Web-Based Sports Centre Previous: Research   Contents

Subsections


Design

There are many aspects of the system to design. Primarily, these are the database behind the system, the appearance, and the actual source code driving it. These will all be covered in the following sections.


Database

The first task when designing any database is to identity the core entities and relationships involved, and construct an Entity-Relation (ER) Diagram based on that.

Initially, the following entities were identified, by reviewing the A3 sheets used by the current booking system.

  • Activity, e.g. Squash, Soccer
  • Venue, e.g. Squash Court 1, Sports Hall 2
  • Venue Group, e.g. Squash Courts, Sports Halls
  • Booking, representing a booking for a given venue at a given time
  • Slot, representing a particular time slot, e.g. 10:00-10:30 (does not specify the date)
  • User, representing a user's online account

Figure: Initial Entity-Relation Diagram for the database
\begin{figure}\begin{center}\epsfig{file=figure/erdiag_initial.eps} \end{center}
\end{figure}

The initial ER diagram constructed is shown in Figure [*]. One relationship worth discussing is activity_venue, which specifies which activities are permitted in which venues. (So that, for example, squash is only permitted in squash courts.) The first conceptual problem with this schema is the relationships between booking, venue, and activity. Figure [*] shows a many-one relationship between booking and venue, and between booking and activity. However, these relationships only require that each booking is for an existing activity, in an existing venue. Therefore, a booking entry specifying the activity ``squash'' in a venue of type ``sunbed'' would be perfectly legal under this schema.

Therefore, the schema was updated, to replace the two aforementioned relationships with a single many-one relationship between booking and activity_venue. This does not actually change the database, because MySQL has no support for foreign keys; it is only a better way of conceptually viewing the relationship, and would make a difference in a DBMS that supports foreign keys. Now, the pair (activity_id, venue_id) from the booking relation must also exist in the activity_venue relation. This will clearly make the example of playing squash in a sunbed illegal, since this combination would never exist in the activity_venue relation.

Another problem with this schema is the simple representation of venues and the activities each venue can be used for. There is no problem for simple venues such as squash courts or sunbeds, but sports halls cause a problem. For example, Sports Hall 1 can be divided in many ways, as shown in Figure [*]. The following points should also be made:

  • The halls can theoretically be divided up in any possible way. For example, at any one time, part A may be used for soccer, while part E is used for a basketball half court!basketball, and parts 7 and 8 are in use for badminton courts.

  • Parts C-F are half courts for basketball; these are often used if only a small number of people wish to play basketball, since it means there are more badminton courts free, which are often in high demand. If a large enough number of people wish to play, they will simply have to book two adjacent parts at the same time.

Figure: Example of how sports halls can be used
\begin{figure}\begin{center}\epsfig{file=figure/sports_hall_example.eps} \end{center}
\end{figure}

This problem was solved, after investigation into possible solutions, using the concept of a compound venue. To easily allow bookings for any permitted sport in such venues, Sports Hall 1A is defined as a compound venue consisting of badminton courts 1-4, and so on.

In terms of the database, this required the addition of the compound_venue relation. This defines a many-many relationship between venue and venue, as shown in Figure [*] (page [*]). This is used to specify venues which are actually comprised of multiple, smaller venues.

A complication arises when a booking for a compound venue is made. When such a venue is booked, a number of entries are automatically placed in the booking relation for the individual parts of the compound venue, as shown in Table [*]. (Fields such as date, time, and user have been omitted for clarity.) This creates a many-one relationship between booking and booking, as shown in Figure [*]. Note that the sub-booking entries are not strictly necessary -- they could be determined by consulting the compound_venue relation for the venue specified by the master booking entry. However, the sub-bookings make operations that check if a venue is booked at a specified time much simpler, because the SQL would be similar to the following:

SELECT * FROM booking WHERE slot_date = $d AND slot_id = $s AND venue_id = $v


Table: Examples of entries in booking relation for a compound booking
Booking ID Master ID Activity Venue ...
1 NULL Soccer Sports Hall 1A ...
2 1 Soccer Badminton Court 1 ...
3 1 Soccer Badminton Court 2 ...
4 1 Soccer Badminton Court 3 ...
5 1 Soccer Badminton Court 4 ...


Before the support for compound venues was introduced, the (Activity, Venue) pair was required to exist as a valid entry in activity_venue, as discussed earlier. (There was no explicit foreign key constraint enforcing this, because MySQL does not support referential integrity constraints.) With compound venues, this restriction can no longer be enforced, as booking entries will be inserted specifying (Activity, Venue) combinations which cannot be made directly. For example, if an indoor soccer pitch is a compound venue comprising four badminton courts, these extra bookings will be for soccer, but in a venue which is actually a badminton court.

Such compound bookings have other minor implications relating to the database integrity. If a row for a part of a compound venue were lost from the booking relation, that part could be double-booked for an activity permitted in that venue. Using the example in Table [*] again, if booking id 3 were deleted, it would be possible for a user to book badminton in Sports Hall 1A (2), even though the whole of Sports Hall 1A was booked for soccer.

Also, it introduces functional dependencies into the booking relation which mean it is no longer normalised, such as master_id $\rightarrow$ slot_idvenue_id. Because this is not a trivial dependency, and master_id is not a superkey of booking, this implies the booking relation is no longer in BCNF (Boyce-Codd Normal Form) [#!korth!#, page 224]. Alternatively, separate relations for bookings and the sub-bookings could be used, as shown in Table [*]. (The left hand relation shown would, as with Table [*], have more columns, such as date, time, and user name.) In fact, in this schema, the sub-booking relation is completely unnecessary, since it would be as easy to determine the sub-bookings from the compound_venue relation, as discussed earlier. Therefore, this schema adds a relation unnecessarily, because if two relations are to be used, it would be better to use booking and compound_venue, rather than booking and an otherwise unnecessary relation.


Table: Alternative schema for compound bookings
Booking ID Activity Venue ...   Booking ID Venue
1 Soccer Sports Hall 1A ...   1 Sports Hall 1A (1)
          1 Sports Hall 1A (2)
          1 Sports Hall 1A (3)
          1 Sports Hall 1A (4)


Yet another alternative would be to include all the sub-bookings in the booking relation, but not to include a master_id field at all, as shown in Table [*]. This is possible since the sub-bookings can be identified by finding all bookings with the same date and time, as the master booking, and which have a venue which is a part of the venue from the master booking:

SELECT b.* FROM booking b, compound_venue cv WHERE b.slot_date = $d AND b.slot_id = $s AND b.venue_id = cv.part_id AND cv.compound_id = $v

The added complication this would require in the code is likely to be worse than using a relation that is not fully BCNF.


Table: Another alternative schema for compound bookings
Booking ID Activity Venue ...
1 Soccer Sports Hall 1A ...
2 Soccer Sports Hall 1A (1) ...
3 Soccer Sports Hall 1A (2) ...
4 Soccer Sports Hall 1A (3) ...
5 Soccer Sports Hall 1A (4) ...


Despite these minor issues, the database design overall is a good one, provided the user interface does not allow the database to enter an inconsistent state, which this system does not. In some cases, a design decision was made to choose convenience over full normalisation, but there are few of these cases, and the implications are all fairly small.

As an example of how the system is careful not to let the database enter an inconsistent state, we shall consider the code which deletes a booking. The code is similar to the following, where $n represents the booking_id of the booking to delete.

DELETE FROM booking WHERE master_id = $n
DELETE FROM booking WHERE booking_id = $n AND master_id IS NULL

This clearly shows that it is not possible to delete only a single part of a compound booking, since the first DELETE will delete all parts, and the second will only delete a booking if it is a master booking (because its master_id is NULL). Therefore, even if a bug in the system (for example, a parameter passed incorrectly by the user interface) meant that $n contained the ID number of a single part of a compound booking, that part would not be deleted by this code.

Using the example from Table [*], with $n=3, no entries would be deleted, because there are no tuples with master_id equal to 3, nor are there any with booking_id equal to 3 and a NULL master_id. The correct way to delete this booking is with $n=1, which using similar logic, will correctly delete the master booking and all the sub-bookings.

The only case in which a single part of a compound booking could be deleted is if the DBMS crashed at a point when a DELETE statement had only partially completed execution. This problem can be avoided if a DBMS supporting transactions and ACID properties [#!korth!#, page 240] is used.

Due to MySQL's lack of support for referential integrity, the system must also be careful to implement these constraints in the business layer.

The functional dependencies are listed in full in Appendix [*]. They show that, with the exception of booking, all relations in the database conform to BCNF. The booking relation conforms to 2NF (Second Normal Form) but nothing higher than that [#!db21!#, page 7-8].

Figure: Final Entity-Relation Diagram for the database
\begin{figure}\begin{center}\epsfig{file=figure/erdiag.eps} \end{center}
\end{figure}

Figure [*] shows the final ER diagram for the database used by this project, and Appendix [*] shows the full database schema.


Appearance

There were two main factors when designing the appearance of the website:

The latter was very easy to achieve, due to the simple design of the Sports Centre website -- the website developed by this project simply uses the same background image and colour scheme, as shown in Figure [*] and Figure [*]. This is only a very simplistic level of similarity, but it has proved to be sufficient to give users the impression that the booking system is connected to the rest of the Sports Centre website. It was chosen to omit the vertical navigation bar, present on the Sports Centre website, from the booking system, simply because some large tables are used, and this navigation bar would occupy too much space on the screen.

Figure: Screenshot of the Sports Centre website
\begin{figure}\begin{center}
\resizebox{10cm}{!}{\epsfig{file=figure/sports_shot.eps}}
\end{center}
\end{figure}

Figure: Screenshot of the Online Booking system
\begin{figure}\begin{center}
\resizebox{10cm}{!}{\epsfig{file=figure/project_shot.eps}}
\end{center}
\end{figure}

The former involved analysing common operations on the website formally, using HCI principles, along with simply asking potential users of the system what they believed could be improved. Further HCI analysis is included in Section [*] (page [*]), and some discussion of the appearance and usability of the site is included in Chapter [*].


Code

In a way, the code is actually the simplest part of the design for a project like this one -- the majority of the code is either querying the database (which was covered in Section [*]) or sending output to the browser (which was covered in Section [*]).

Each page of the site is contained within a different source file, so each file is fairly small and self-contained (the largest source file is 15KB). Additionally, a library of common functions was created, and included using the PHP include statement from each source file. Functions in this file range from very general functions, to very specific functions, as shown below.

  • General functions, used by almost all pages:

    • dbconnect(): Connects to the database, and stored the connection handle in a global variable $dbh

    • site_header(): Prints out the common header for each HTML page

    • check_login(): Checks that the user is logged in (see Section [*]) and shows a login form otherwise. This function makes it very easy to keep the site secure, since on any page requiring an authenticated user, a call to this function must simply be made near to the beginning of the program.

  • Specific functions, used only by a small number of pages:

    • find_booking(): Checks whether there is a booking at a given time in a given venue

    • send_intro_email(): Sends an email, either when a user signs up, or when they request that their password be reset

This only shows a very small proportion of the total number of functions; in total there are approximately 40 functions.


next up previous contents
Next: Implementation Up: A Web-Based Sports Centre Previous: Research   Contents
© 2002-2012 Ben Smithurst <web.1d36ca20@bensmithurst.com>