-
Notifications
You must be signed in to change notification settings - Fork 191
Description
Description
Summary of issue: It is not clear how to define a table so that a record user can insert records, but it appears that a CREATE permission and a default owner field are required. I do not believe this is documented clearly but seems to be the first thing people will run into (as I did) when working with record users.
To enable record users, I defined a user table like this:
DEFINE TABLE user SCHEMAFULL
PERMISSIONS
FOR select, update, delete WHERE id = $auth.id;
DEFINE FIELD user_id ON user TYPE string;
DEFINE FIELD email ON user TYPE string ASSERT string::is::email($value);
DEFINE INDEX email ON user FIELDS email UNIQUE;
DEFINE INDEX user_id ON user FIELDS user_id UNIQUE;
DEFINE ACCESS user ON DATABASE TYPE RECORD
SIGNIN (
SELECT * FROM user WHERE email = $email AND user_id = $user_id
)
SIGNUP (
CREATE user CONTENT {
email: $email,
user_id: $user_id
}
);This is described here (https://surrealdb.com/docs/surrealdb/security/authentication), as well as how to sign in and sign up as a record user.
However, I did not find documentation that explains the correct way to define additional tables that the record user will access.
In my use case, I have a logs table that will allow the user to create logs. I created it like this:
DEFINE TABLE test_logs SCHEMALESS
PERMISSIONS
FOR select, update, delete WHERE owner = $auth.id;If I then run the following code to write to the table:
export async function get_db(){
let db = new Surreal();
await db.connect(url, {namespace:"production", database :"main"}) ;
let token = await db.signin({namespace:"production", database :"main", access : 'user', variable\
s : {email : "[email protected]", user_id :"1234"}}) ;
log(`Connected as [email protected] and got token: ${token}`)
return db
}
let db = await get_db() ; //connects and logs user token
let r = await db.query("INSERT INTO test_logs { test_data : 3 } "); // => returns empty array [ [ ] ] I simply get an empty array [ [ ] ] , without any explanation.
With some experimentation and looking at the code examples (https://github.com/surrealdb/examples/blob/main/notes-v2/src/schema/sticky.surql) ,
I found that a minimal working example is the following:
DEFINE TABLE test_logs SCHEMALESS
PERMISSIONS
FOR create WHERE $auth.id != NONE -- this seems necessary (but not sufficient)
FOR select, update, delete WHERE owner = $auth.id;
DEFINE FIELD owner ON TABLE test_logs
TYPE record<user>
--VALUE $before OR $auth.id -- this does ?not seem necessary (but if only this and no default then same issue)
DEFAULT $auth.id; -- this seems necessaryAfter this then:
let r = await db.query("INSERT INTO test_logs { test_data : 3 } "); // => returns [ [ { id: [_RecordId], owner: [_RecordId], test_data: 3 } ] ]Overall it seems that the create permissions are necessary and that the DEFAULT $auth.id permissions are necessary on the owner field in order to get the query to work properly.
Simply having the CREATE statement alone was not sufficient, nor was having the CREATE statement + the VALUE. The referenced examples above use both VALUE and DEFAULT as well, which doesn't necessarily help clarify what is actually necessary. The reason why DEFAULT works but not VALUE is not clear to me.
Is this documented somewhere that I am missing? Please help me understand the minimal required, and why. And I would be happy to help contribute to the docs via PR too!
Finally, if there is a way to get feedback about why the query returned an empty array/ didn't insert any records, that would be helpful for debugging - is this available somehow? The empty array was mysterious...
Is there an existing issue for this?
- I have searched the existing issues
Code of Conduct
- I agree to follow this project's Code of Conduct