I had been thinking of adding a database to Plan 9 for a while. Here's my design:

The DBMS is a 9P server. Upon mounting, it takes as arguments two files:
        - the list of names of records and fields
        - the data itself
It then parses the data into virtual files in the location given with the mount command.

For example, let's say I have a customer database for a kitchenware distributor stored in two files: customer_fields (the list of field and record names) and customer_data. I can load it with:

        9dbms
        mount /srv/9dbms /n/customers customer_fields customer_data

If that's not possible, these two filenames are stored in another file.

Now here's what this /n/customers will have. If the fields file looks like this:

        !record:uvlong # records are numbered
        name:string * 1
        address:string * 2
        phoneno:string[10]
        wants:list of string

and we have customers numbered 4, 9, and 30:

        cpu% cd /n/database
        cpu% ls
        4
        9
        30
        cpu% ls 4
        name
        address
        phoneno
        wants
        cpu% cat 4/wants
        3 of 30-inch deep pots
        4 sets of 20 Imperial-grade steel forks
        cpu%

You see what's going on? The use of 9P means there will be NO special API for accessing the database: you just use open, read, write, &c, or rc and the standard tools. This makes report generation a breeze:

        #!/bin/rc
        rfork e
        cd /n/database
        {
                echo '.DS'
                for(i in *){
                        cat $i/name
                        cat $i/address
                        cat $i/phoneno
                        echo 'REQUESTS:
                        cat $i/wants
                        echo
                }
                echo '.DE'
        } | troff -ms

Or, for a more elaborate report:

        #!/bin/rc
        rfork e
        cd /n/database
        {
                cat <<\END
                .TS
                center;
                c s
                lfB lfB lfB lfB
                l l l l.
                \fBREPORT\fP
                Name    Address Phone Number    Wants
                END
                for(i in *){
                        cd $i
                        name=`{cat name}
                        addr=`{cat address}
                        pn=`{cat phoneno}
                        echo $"name^'      '^$"addr^' '^$"pn^'   T{'
                        cat wants
                        echo 'T}'
                        cd ..
                }
        } | tbl | troff -ms

Then, if you use bitsy, you can write a program with libcontrol and the networking commands to make a portable remote customer editor!


Reply via email to