Changes between Version 66 and Version 67 of BluePrintAuthorization


Ignore:
Timestamp:
06/20/10 08:15:00 (11 years ago)
Author:
Fran Boon
Comment:

SQLFORM2() to have a single DAL hit

Legend:

Unmodified
Added
Removed
Modified
  • BluePrintAuthorization

    v66 v67  
    149149
    150150 * For single records modify {{{shn_has_permission()}}} (called from {{{shn_create()}}}, {{{shn_delete()}}}, {{{shn_read()}}} & {{{shn_update()}}}, but also available for other functions)
    151   * Q: Can we merge this with the reading of the record to have a single DAL hit instead of 1 for the permissions check & another for the actual read?
     151  * Where possible, we merge this with the reading of the record to have a single DAL hit instead of 1 for the permissions check & another for the actual read by modifying the calling functions appropriately:
     152   * {{{modules/sahana.py}}} defines a new SQLFORM2() class which takes a record instead of a record_id
     153   * {{{CrudS3}}} modifies {{{Crud.create()}}} to take a record instead of a record_id & calls {{{SQLFORM2()}}}
     154   * {{{CrudS3}}} modifies {{{Crud.update()}}} to take a record instead of a record_id & calls {{{SQLFORM2()}}}
    152155{{{
    153156def shn_has_permission(name, tablename, record_id = 0):
    154157    """
    155158        S3 framework function to define whether a user can access a record in manner "name"
     159        - if checking a table (record_id = 0), then it returns Boolean
     160        - if checking a record (record_id > 0), then it returns the record or None
    156161    """
    157162
     
    202207    if record_id and authorised:
    203208
    204         record = None
    205 
    206209        _fields = table.fields
     210
     211        # We pull back the full record rather than just the fields needed to check permisisons,
     212        # so that the caller doesn't need to make a 2nd DAL call to access the data
     213        record = db(table.id == record_id).select(limitby=(0, 1)).first()
    207214
    208215        if "deleted" in  _fields:
    209216            # Check if record is deleted
    210             if "reader_id" in _fields and "created_by" in _fields:
    211                 record = db(table.id == record_id).select(table.deleted, table.reader_id, table.writer_id, table.created_by, limitby=(0, 1)).first()
    212             elif "reader_id" in _fields:
    213                 record = db(table.id == record_id).select(table.deleted, table.reader_id, table.writer_id, limitby=(0, 1)).first()
    214             elif "created_by" in _fields:
    215                 record = db(table.id == record_id).select(table.deleted, table.created_by, limitby=(0, 1)).first()
    216             else:
    217                 record = db(table.id == record_id).select(table.deleted, limitby=(0, 1)).first()
    218 
    219217            if record.deleted:
    220                 authorised = False
    221                 return authorised
    222 
    223         elif 1 in roles:
     218                record = None
     219                return record
     220
     221        if 1 in roles:
    224222            # Admin is always authorised to view undeleted data (deleted data accessible through alternate UI)
    225             authorised = True
    226             return authorised
    227 
    228         # Check the record's auth fields
     223            return record
     224
    229225        if not "reader_id" in _fields:
    230226            # No record-level permissions (we assume that reader_id & writer_id fields always present/absent together via use of 'permissions_id')
    231             authorised = True
    232             return authorised
    233 
    234         if not record:
    235             if "created_by" in _fields:
    236                 record = db(table.id == record_id).select(table.reader_id, table.writer_id, table.created_by, limitby=(0, 1)).first()
    237             else:
    238                 record = db(table.id == record_id).select(table.reader_id, table.writer_id, limitby=(0, 1)).first()
     227            return record
     228
     229        # Check the record's auth fields
    239230        if name == "read":
    240231            if not table.reader_id:
    241                 authorised = True
     232                return record
    242233            else:
    243234                authorised = False
     
    251242                        if auth.user.id == table.created_by:
    252243                            authorised = True
     244                if not authorised:
     245                    record = None
     246                return record
    253247               
    254248        elif name in ["delete", "update"]:
    255249            if not table.writer_id:
    256                 authorised = True
     250                return record
    257251            else:
    258252                authorised = False
     
    267261                        if auth.user.id == table.created_by:
    268262                            authorised = True
     263                if not authorised:
     264                    record = None
     265                return record
    269266
    270267        else:
     
    273270            redirect(URL(r=request, f="index"))
    274271
    275 return authorised
     272if record_id:
     273    return None
     274else:
     275    return authorised
    276276}}}
    277277