             project_id  : required
             path        : required
             cb          : required
+        if not @_validate_uuids(opts) then return
         x = {}; x[opts.path] = true
         db.table('projects').get(opts.project_id).replace(@r.row.without(public_paths:x)).run(opts.cb)
 
     _validate_uuids: (opts) =>
         for k, v of opts
             if k.slice(k.length-2) == 'id'
-                if not misc.is_valid_uuid_string(v)
+                if v? and not misc.is_valid_uuid_string(v)
                     opts.cb("invalid #{k} -- #{v}")
                     return false
+            if k.slice(k.length-3) == 'ids'
+                for w in v
+                    if not misc.is_valid_uuid_string(w)
+                        opts.cb("invalid uuid #{w} in #{k} -- #{misc.to_json(v)}")
+                        return false
         return true
 
     add_user_to_project: (opts) =>

        opts = defaults opts,
            project_id  : required
            cb          : required
        @db.table('projects').get(opts.project_id).pluck('public_paths').run (err, x) =>
            opts.cb(err, x?.public_paths)   # map {path:description}


            account_id  : required
            groups      : required  # array of elts of PROJECT_GROUPS above
            cb          : required  # cb(err)
        if not @_validate_uuids(opts) then return

    # all id's of projects having anything to do with the given account (ignores
    # hidden projects unless opts.hidden is true).
