Last active
April 6, 2024 02:04
-
-
Save koakh/fbbc37cde630bedcf57acfd4d6a6956b to your computer and use it in GitHub Desktop.
SurrealDB : How to use signin and signup (server + client nodesjs)
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
**As a developer you have complete control over the signup and signin functionality...** | |
```shell | |
$ surreal sql --conn http://localhost:8000 --user root --pass root --ns test --db test | |
``` | |
```sql | |
-- optional : this is the default see --ns test --db test start server flags | |
-- USE NS test DB test; | |
-- define TABLE user SCHEMAFULL PERMISSIONS FOR select, update WHERE id = $auth.id FOR create, delete NONE; // miss , | |
-- Tobie: However, make it schemaless, as you haven't defined fields. | |
-- SCHEMAFULL if we defined fields else use SCHEMALESS | |
---opt1:SCHEMALESS | |
-- DEFINE TABLE user SCHEMALESS | |
-- PERMISSIONS | |
-- FOR select, update WHERE id = $auth.id, | |
-- FOR create, delete NONE; | |
-- warn with opt1 if we re signup again it will create another user with same email, and after it all signin's will fail, | |
-- to fix this issue always use next opt2 that have a UNIQUE INDEX, and prevents create a user with same email, and this is the expected behavior | |
---opt2:SCHEMAFULL | |
DEFINE TABLE user SCHEMAFULL | |
PERMISSIONS | |
FOR select, update WHERE id = $auth.id, | |
FOR create, delete NONE; | |
DEFINE FIELD user ON user TYPE string; | |
DEFINE FIELD pass ON user TYPE string; | |
DEFINE FIELD settings.* ON user TYPE object; | |
DEFINE FIELD settings.marketing ON user TYPE string; | |
DEFINE FIELD tags ON user TYPE array; | |
DEFINE INDEX idx_user ON user COLUMNS user UNIQUE; | |
-- define scope | |
DEFINE SCOPE allusers | |
-- the JWT session will be valid for 14 days | |
SESSION 14d | |
-- The optional SIGNUP clause will be run when calling the signup method for this scope | |
-- It is designed to create or add a new record to the database. | |
-- If set, it needs to return a record or a record id | |
-- The variables can be passed in to the signin method | |
SIGNUP ( CREATE user SET settings.marketing = $marketing, user = $user, pass = crypto::argon2::generate($pass), tags = $tags ) | |
-- The optional SIGNIN clause will be run when calling the signin method for this scope | |
-- It is designed to check if a record exists in the database. | |
-- If set, it needs to return a record or a record id | |
-- The variables can be passed in to the signin method | |
SIGNIN ( SELECT * FROM user WHERE user = $user AND crypto::argon2::compare(pass, $pass) ) | |
-- this optional clause will be run when calling the signup method for this scope | |
``` | |
ctrl+c | |
check info db in shell | |
```shell | |
$ echo "INFO FOR DB;" | surreal sql --conn http://localhost:8000 --user root --pass root --ns test --db test | jq | |
``` | |
check info db in REPL | |
```shell | |
$ surreal sql --conn http://localhost:8000 --user root --pass root --ns test --db test --pretty | |
``` | |
```sql | |
INFO FOR DB; | |
``` | |
```json | |
[ | |
{ | |
"time": "249.753µs", | |
"status": "OK", | |
"result": { | |
"dl": {}, | |
"dt": {}, | |
"sc": { | |
"allusers": "DEFINE SCOPE allusers SESSION 2w SIGNUP (CREATE user SET settings.marketing = $marketing, email = $email, pass = crypto::argon2::generate($pass), tags = $tags) SIGNIN (SELECT * FROM user WHERE email = $email AND crypto::argon2::compare(pass, $pass))" | |
}, | |
"tb": { | |
"user": "DEFINE TABLE user SCHEMALESS PERMISSIONS FOR select WHERE id = $auth.id, FOR create NONE, FOR update WHERE id = $auth.id, FOR delete NONE" | |
} | |
} | |
} | |
] | |
``` | |
Then you could use the **following query from the client to signup (create) a new user**, or **signin (select) an existing user**... | |
```js | |
db.signup({ | |
NS: 'my_ns', | |
DB: 'my_db', | |
SC: 'allusers', // We want to signup to the 'allusers' scope defined above | |
email: '[email protected]', // We can add any variable here to use in the SIGNUP clause | |
pass: 'some password', // We can add any variable here to use in the SIGNUP clause | |
marketing: true, // We can add any variable here to use in the SIGNUP clause | |
tags: ['rust', 'golang', 'javascript'], // We can add any variable here to use in the SIGNUP clause | |
}); | |
// you should receive a jwt token | |
db.signin({ | |
NS: 'my_ns', | |
DB: 'my_db', | |
SC: 'allusers', // We want to signup to the 'allusers' scope defined above | |
email: '[email protected]', // We can add any variable here to use in the SIGNUP clause | |
pass: 'some password', // We can add any variable here to use in the SIGNUP clause | |
}); | |
// you should receive a jwt token | |
``` |
I am using the signup function and providing a username and password. After that I use the signin function with the same username but with the a different password, I was expecting an error but I still got a token also calling the authenticate function after that did not throw an error. How is this possible? What am I doing wrong?
await db.signup({
NS: "mydb",
DB: "mydb",
SC: "allusers",
user: "jane",
password: "jane",
email: "[email protected]",
});
const token = await db.signin({
NS: "mydb",
DB: "mydb",
SC: "allusers",
user: "jane",
password: "jane1",
});
await db.authenticate(token)
All of this still works even though I give an incorrect pass while signin
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
@koakh hi, can you help us with argon2 https://github.com/orgs/surrealdb/discussions/2196#discussioncomment-6314556
Thanks for the great guidance