> ## Documentation Index
> Fetch the complete documentation index at: https://docs-dev-actions-triggers-prototype.mintlify.site/llms.txt
> Use this file to discover all available pages before exploring further.

# Créer des modèles de script

> Cet article décrit les modèles de scripts d’action personnalisés des bases de données pour la création des utilisateurs.

Le script Créer implémente la fonction définie lors de la création d’un utilisateur. Nous recommandons de nommer cette fonction `create`.

Ce script est facultatif. Si cette option est activée, lorsqu’un utilisateur s’inscrit via la connexion universelle ou est créé via <Tooltip href="/docs/fr-ca/glossary?term=auth0-dashboard" tip="Auth0 Dashboard
Principal produit d’Auth0 pour configurer vos services." cta="Voir le glossaire">Auth0 Dashboard</Tooltip> ou <Tooltip href="/docs/fr-ca/glossary?term=management-api" tip="Management API
Un produit permettant aux clients d’effectuer des tâches administratives." cta="Voir le glossaire">Management API</Tooltip> Auth0, Auth0 exécutera le script pour créer un enregistrement utilisateur correspondant dans la base de données externe.

Lorsqu’un utilisateur est créé dans Auth0, Auth0 appelle une série de scripts :

1. [Obtenir utilisateur](/docs/fr-ca/authenticate/database-connections/custom-db/templates/get-user) : vérifie que l’utilisateur n’existe pas déjà dans Auth0 ou dans la base de données externe.
2. Créer : permet de créer l’utilisateur de la base de données externe.
3. [Connexion](/docs/fr-ca/authenticate/database-connections/custom-db/templates/login) : vérifie que l’utilisateur a été créé avec succès.

## Fonction Créer

La fonction `Create` permet de :

* envoyer les profil de l’utilisateur des données à l’API de la base de données externe.
* renvoyer une erreur si la création de l’utilisateur échoue.

### Définition

La fonction `create` accepte deux paramètres et renvoie une fonction de `callback` :

```javascript lines theme={null}
create(user, callback): function
```

| Paramètre  | Type     | Description                                                                                                            |
| ---------- | -------- | ---------------------------------------------------------------------------------------------------------------------- |
| `user`     | Objet    | Contient les [données de profil utilisateur](#user-object-parameter) tirées du processus de création de l’utilisateur. |
| `callback` | Fonction | Utilisée pour transmettre les données d’erreur dans le pipeline.                                                       |

### Exemple

Voici un exemple fictif en JavaScript de la manière dont vous pourriez implémenter la fonction `create`. Pour des exemples spécifiques à un langage, consultez [Exemples de scripts spécifiques à un langage](#language-specific-script-examples).

```javascript lines theme={null}
function create(user, callback) {
  // Send user profile data to external database API
  let hashedPassword = hash(user.password);

  let options = {
    url: "https://example.com/api/create",
    body: {
      email: user.email,
      username: user.username,
      password: hashedPassword
    }
  };

  send(options, err => {
    // Return error in callback if user already exists
    if (err && err.id === "USER_ALREADY_EXISTS") {
      return callback(new ValidationError("user_exists", "My custom error message."));
    } else if (err) {
      // Return error in callback if error occurred
      return callback(new Error("My custom error message."));
    }

    // Return `null` value in callback if user creation operation succeeded
    return callback(null);
  });
}
```

### Chiffrement

<Warning>
  Évitez d’enregistrer, de stocker ou de transporter le mot de passe n’importe où sous sa forme non cryptée.
</Warning>

Chiffrez la valeur du mot de passe à l’aide d’une bibliothèque de chiffrement de hachage cryptographique telle que `bcrypt` afin d’éviter toute fuite de données potentielle.

#### Exemple

```javascript lines theme={null}
bcrypt.hash(password, 10, function (err, hash) {
    if (err) {
        return callback(err);
    } else {
        // Return hashed password
    }
});
```

## Fonction de rappel

La fonction de `callback` accepte un paramètre et renvoie une fonction.

### Définition

```javascript lines theme={null}
callback(error): function
```

| Paramètre | Type  | Requis | Description                    |
| --------- | ----- | ------ | ------------------------------ |
| `error`   | Objet | Requis | Contient des données d’erreur. |

### Retourne un succès

Si l’opération de création de l’utilisateur a réussi, renvoyez la fonction de `callback` et passer une valeur `null` comme paramètre `error` paramètre.

#### Exemple

```javascript lines theme={null}
return callback(null);
```

### Renvoyer une erreur

Si une erreur survient, renvoyez la fonction de rappel, et transmettez l’information pertinente concernant l’erreur au paramètre `error` :

#### Objet de type ValidationError

L’objet de type erreur personnalisé `ValidationError` vous permet de transmettre des données qui seront affichées dans vos [Journaux du locataire](/docs/fr-ca/deploy-monitor/logs).

##### Constructeur

Le constructeur `ValidationError` accepte jusqu’à deux paramètres :

```javascript lines theme={null}
new ValidationError(errorCode[, message]): ValidationError
```

| Paramètre   | Description                                                  |
| ----------- | ------------------------------------------------------------ |
| `errorCode` | (Requis) Chaîne. Indique le type d’erreur.                   |
| `message`   | (Facultatif) Chaîne. Contient des informations sur l’erreur. |

#### Renvoie une erreur indiquant que l’utilisateur existe déjà

Si vous renvoyez une erreur avec la valeur `user_exists` pour le paramètre `errorCode`, Auth0 enregistrera un événement du journal du locataire `fs`.

##### Exemple

```javascript lines theme={null}
return callback(new ValidationError("user_exists", "My custom error message."));
```

| Champ Événement de journal des locataires | Valeur                     |
| ----------------------------------------- | -------------------------- |
| **Code**                                  | `fs`                       |
| **Événement**                             | Échec d’inscription        |
| **Description**                           | `My custom error message.` |

## Paramètre d’objet utilisateur

Le paramètre d’objet `user` contient un ensemble prédéfini de propriétés provenant du processus de création de l’utilisateur :

| Propriété       | Description                                                                                                                                                                                                                       |
| --------------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `client_id`     | L’ID client de l’application Auth0 si l’utilisateur s’est inscrit par la connexion universelle, ou la clé API si l’utilisateur a été créé par l’Auth0 Dashboard ou par Management API.                                            |
| `tenant`        | Le nom du locataire Auth0.                                                                                                                                                                                                        |
| `email`         | L’adresse courriel de l’utilisateur.                                                                                                                                                                                              |
| `password`      | Le mot de passe de l’utilisateur en texte brut.                                                                                                                                                                                   |
| `username`      | Le nom d’utilisateur de l’utilisateur. Requis uniquement si le paramètre [**Nécessite le nom d’utilisateur**](/docs/fr-ca/connections/database/require-username) est activé pour la connexion à la base de données personnalisée. |
| `connection`    | Le nom de la connexion Auth0.                                                                                                                                                                                                     |
| `user_metadata` | Contient les propriétés de l’objet `user_metadata` sur le profil Auth0 de l’utilisateur, si l’objet existe.                                                                                                                       |
| `app_metadata`  | Contient les propriétés de l’objet `app_metadata` sur le profil Auth0 de l’utilisateur, si l’objet existe.                                                                                                                        |

### Propriété du nom d’utilisateur

Si votre connexion à la base de données personnalisée a le paramètre [Requires Username](/docs/fr-ca/authenticate/database-connections/require-username) activé, alors les scripts [Login](/docs/fr-ca/authenticate/database-connections/custom-db/templates/login) et [Get User](/docs/fr-ca/authenticate/database-connections/custom-db/templates/get-user) doivent prendre en charge la propriété `username`, vous devez donc la stocker dans votre base de données externe.

### Métadonnées de l’utilisateur et de l’application

Les propriétés `user_metadata` et `app_metadata` n’ont pas besoin d’être stockées dans votre base de données externe. Auth0 stocke automatiquement ces valeurs dans le cadre de l’enregistrement de profil utilisateur créé en interne.

### Champs d’inscription personnalisés

Si vous [créez et utilisez des champs personnalisés](/docs/fr-ca/libraries/custom-signup#using-the-api) pendant le processus d’inscription, ils seront inclus dans l’objet `user`.

### Exemple

```javascript lines theme={null}
{
    client_id: "8tkMo6n1QkKOazqPcSQd8wU7LzXYibgK",
    tenant: "{yourAuth0Tenant}",
    email: "username@domain.com",
    password: "mySuperSecretPassword123",
    username: "username456",
    user_metadata: {
        "language": "en"
    },
    app_metadata: {
        "plan": "full"
    }
}
```

## Exemples de scripts propres à une langue

Auth0 fournit des exemples de scripts à utiliser avec les langages/technologies ci-dessous :

* [JavaScript](#javascript)
* [Fournisseur d’appartenances ASP.NET (MVC3 – Fournisseurs universels)](#asp-net-membership-provider-mvc3-universal-providers-)
* [Fournisseur d’appartenances ASP.NET (MVC4 – Appartenance simple)](#asp-net-membership-provider-mvc4-simple-membership-)
* [MongoDB](#mongodb)
* [MySQL](#mysql)
* [PostgreSQL](#postgresql)
* [SQL Server](#sql-server)
* [Base de données SQL Windows Azure](#windows-azure-sql-database)
* [Demande avec Basic Auth](#request-with-basic-auth)

### JavaScript

```javascript lines theme={null}
function create(user, callback) {
  // This script should create a user entry in your existing database. It will
  // be executed when a user attempts to sign up, or when a user is created
  // through the Auth0 Dashboard or Management API.
  // When this script has finished executing, the Login script will be
  // executed immediately afterwards, to verify that the user was created
  // successfully.
  //
  // The user object will always contain the following properties:
  // * email: the user's email
  // * password: the password entered by the user, in plain text
  // * tenant: the name of this Auth0 account
  // * client_id: the client ID of the application where the user signed up, or
  //              API key if created through the Management API or Auth0 Dashboard
  // * connection: the name of this database connection
  //
  // There are three ways this script can finish:
  // 1. A user was successfully created
  //     callback(null);
  // 2. This user already exists in your database
  //     callback(new ValidationError("user_exists", "my error message"));
  // 3. Something went wrong while trying to reach your database
  //     callback(new Error("my error message"));
  const msg = 'Please implement the Create script for this database connection ' +
    'at https://manage.auth0.com/#/connections/database';
  return callback(new Error(msg));
}
```

### Fournisseur d’appartenances ASP.NET (MVC3 – Fournisseurs universels)

```javascript lines theme={null}
function create(user, callback) {
  const crypto = require('crypto');
  const sqlserver = require('tedious@1.11.0');
  const Connection = sqlserver.Connection;
  const Request = sqlserver.Request;
  const TYPES = sqlserver.TYPES;
  const connection = new Connection({
    userName: 'the username',
    password: 'the password',
    server: 'the server',
    options: {
      database: 'the db name',
      encrypt: true,
      // Required to retrieve userId needed for Membership entity creation
      rowCollectionOnRequestCompletion: true
    }
  });
  const applicationId = 'your-application-id-goes-here';
  /**
   * hashPassword
   *
   * This function creates a hashed version of the password to store in the database.
   *
   * @password  {[string]}      the password entered by the user
   * @return    {[string]}      the hashed password
   */
  function hashPassword(password, salt) {
    // the default implementation uses HMACSHA256 and since Key length is 64
    // and default salt is 16 bytes, Membership will fill the buffer repeating the salt
    const key = Buffer.concat([salt, salt, salt, salt]);
    const hmac = crypto.createHmac('sha256', key);
    hmac.update(Buffer.from(password, 'ucs2'));
    return hmac.digest('base64');
  }
  connection.on('debug', function(text) {
    // if you have connection issues, uncomment this to get more detailed info
    // console.log(text);
  }).on('errorMessage', function(text) {
    // this will show any errors when connecting to the SQL database or with the SQL statements
    console.log(JSON.stringify(text));
  });
  connection.on('connect', function(err) {
    if (err) {
      return callback(err);
    }
    createMembershipUser(user, function(err, user) {
      if (err) return callback(err); // this will return a 500
      if (!user) return callback(); // this will return a 401
      callback(null, user);
    });
  });
  function createMembershipUser(user, callback) {
    const userData = {
      UserName: user.email,
      ApplicationId: applicationId
    };
    const createUser =
      'INSERT INTO Users (UserName, LastActivityDate, ApplicationId, UserId, IsAnonymous) ' +
      'OUTPUT Inserted.UserId ' +
      'VALUES (@UserName, GETDATE(), @ApplicationId, NEWID(), \'false\')';
    const createUserQuery = new Request(createUser, function(err, rowCount, rows) {
      if (err) return callback(err);
      // No records added
      if (rowCount === 0) return callback(null);
      const userId = rows[0][0].value;
      const salt = crypto.randomBytes(16);
      const membershipData = {
        ApplicationId: applicationId,
        Email: user.email,
        Password: hashPassword(user.password, salt),
        PasswordSalt: salt.toString('base64'),
        UserId: userId
      };
      const createMembership =
        'INSERT INTO Memberships (ApplicationId, UserId, Password, PasswordFormat, ' +
        'PasswordSalt, Email, isApproved, isLockedOut, CreateDate, LastLoginDate, ' +
        'LastPasswordChangedDate, LastLockoutDate, FailedPasswordAttemptCount, ' +
        'FailedPasswordAttemptWindowStart, FailedPasswordAnswerAttemptCount, ' +
        'FailedPasswordAnswerAttemptWindowsStart) ' +
        'VALUES ' +
        '(@ApplicationId, @UserId, @Password, 1, @PasswordSalt, ' +
        '@Email, \'false\', \'false\', GETDATE(), GETDATE(), GETDATE(), GETDATE(), 0, 0, 0, 0)';
      const createMembershipQuery = new Request(createMembership, function(err, rowCount) {
        if (err) return callback(err);
        if (rowCount === 0) return callback(null);
        callback(null, rowCount > 0);
      });
      createMembershipQuery.addParameter('ApplicationId', TYPES.VarChar, membershipData.ApplicationId);
      createMembershipQuery.addParameter('Email', TYPES.VarChar, membershipData.Email);
      createMembershipQuery.addParameter('Password', TYPES.VarChar, membershipData.Password);
      createMembershipQuery.addParameter('PasswordSalt', TYPES.VarChar, membershipData.PasswordSalt);
      createMembershipQuery.addParameter('UserId', TYPES.VarChar, membershipData.UserId);
      connection.execSql(createMembershipQuery);
    });
    createUserQuery.addParameter('UserName', TYPES.VarChar, userData.UserName);
    createUserQuery.addParameter('ApplicationId', TYPES.VarChar, userData.ApplicationId);
    connection.execSql(createUserQuery);
  }
}
```

### Fournisseur d’appartenances ASP.NET (MVC4 – Appartenance simple)

```javascript lines theme={null}
function create(user, callback) {
  const crypto = require('crypto');
  const sqlserver = require('tedious@1.11.0');
  const Connection = sqlserver.Connection;
  const Request = sqlserver.Request;
  const TYPES = sqlserver.TYPES;
  const connection = new Connection({
    userName: 'the username',
    password: 'the password',
    server: 'the server',
    options: {
      database: 'the db name',
      encrypt: true,
      // Required to retrieve userId needed for Membership entity creation
      rowCollectionOnRequestCompletion: true
    }
  });
  /**
   * hashPassword
   *
   * This function hashes a password using HMAC SHA256 algorithm.
   *
   * @password    {[string]}    password to be hased
   * @salt        {[string]}    salt to be used in the hashing process
   * @callback    {[function]}  callback to be called after hashing the password
   */
  function hashPassword(password, salt, callback) {
    const iterations = 1000;
    const passwordHashLength = 32;
    crypto.pbkdf2(password, salt, iterations, passwordHashLength, 'sha1', function (err, hashed) {
      if (err) return callback(err);
      const result = Buffer.concat([Buffer.from([0], 1), salt, Buffer.from(hashed, 'binary')]);
      const resultBase64 = result.toString('base64');
      callback(null, resultBase64);
    });
  }
  connection.on('debug', function (text) {
    // if you have connection issues, uncomment this to get more detailed info
    // console.log(text);
  }).on('errorMessage', function (text) {
    // this will show any errors when connecting to the SQL database or with the SQL statements
    console.log(JSON.stringify(text));
  });
  connection.on('connect', function (err) {
    if (err) return callback(err);
    const createUser =
      'INSERT INTO UserProfile (UserName) ' +
      'OUTPUT Inserted.UserId ' +
      'VALUES (@UserName)';
    const createUserQuery = new Request(createUser, function (err, rowCount, rows) {
      if (err || rowCount === 0) return callback(err);
      const userId = rows[0][0].value;
      const salt = crypto.randomBytes(16);
      const createMembership =
        'INSERT INTO webpages_Membership ' +
        '(UserId, CreateDate, IsConfirmed, PasswordFailuresSinceLastSuccess, Password, PasswordSalt) ' +
        'VALUES ' +
        '(@UserId, GETDATE(), \'false\', 0, @Password, \'\')';
      const createMembershipQuery = new Request(createMembership, function (err, rowCount) {
        if (err || rowCount === 0) return callback(err);
        callback(null, rowCount > 0);
      });
      hashPassword(user.password, salt, function (err, hashedPassword) {
        if (err) return callback(err);
        createMembershipQuery.addParameter('Password', TYPES.VarChar, hashedPassword);
        createMembershipQuery.addParameter('PasswordSalt', TYPES.VarChar, salt.toString('base64'));
        createMembershipQuery.addParameter('UserId', TYPES.VarChar, userId);
        connection.execSql(createMembershipQuery);
      });
    });
    createUserQuery.addParameter('UserName', TYPES.VarChar, user.email);
    connection.execSql(createUserQuery);
  });
}
```

### MongoDB

```javascript lines theme={null}
function create(user, callback) {
  const bcrypt = require('bcrypt');
  const MongoClient = require('mongodb@3.1.4').MongoClient;
  const client = new MongoClient('mongodb://user:pass@mymongoserver.com');
  client.connect(function (err) {
    if (err) return callback(err);
    const db = client.db('db-name');
    const users = db.collection('users');
    users.findOne({ email: user.email }, function (err, withSameMail) {
      if (err || withSameMail) {
        client.close();
        return callback(err || new Error('the user already exists'));
      }
      bcrypt.hash(user.password, 10, function (err, hash) {
        if (err) {
          client.close();
          return callback(err);
        }
        user.password = hash;
        users.insert(user, function (err, inserted) {
          client.close();
          if (err) return callback(err);
          callback(null);
        });
      });
    });
  });
}
```

### MySQL

```javascript lines theme={null}
function create(user, callback) {
  const mysql = require('mysql');
  const bcrypt = require('bcrypt');
  const connection = mysql({
    host: 'localhost',
    user: 'me',
    password: 'secret',
    database: 'mydb'
  });
  connection.connect();
  const query = 'INSERT INTO users SET ?';
  bcrypt.hash(user.password, 10, function(err, hash) {
    if (err) return callback(err);
    const insert = {
      password: hash,
      email: user.email
    };
    connection.query(query, insert, function(err, results) {
      if (err) return callback(err);
      if (results.length === 0) return callback();
      callback(null);
    });
  });
}
```

### PostgreSQL

```javascript lines theme={null}
function create(user, callback) {
  //this example uses the "pg" library
  //more info here: https://github.com/brianc/node-postgres
  const bcrypt = require('bcrypt');
  const postgres = require('pg');
  const conString = 'postgres://user:pass@localhost/mydb';
  postgres.connect(conString, function (err, client, done) {
    if (err) return callback(err);
    bcrypt.hash(user.password, 10, function (err, hashedPassword) {
      if (err) return callback(err);
      const query = 'INSERT INTO users(email, password) VALUES ($1, $2)';
      client.query(query, [user.email, hashedPassword], function (err, result) {
        // NOTE: always call `done()` here to close
        // the connection to the database
        done();
        return callback(err);
      });
    });
  });
}
```

### SQL Server

```javascript lines theme={null}
function create(user, callback) {
  //this example uses the "tedious" library
  //more info here: http://pekim.github.io/tedious/index.html
  const bcrypt = require('bcrypt');
  const sqlserver = require('tedious@1.11.0');
  const Connection = sqlserver.Connection;
  const Request = sqlserver.Request;
  const TYPES = sqlserver.TYPES;
  const connection = new Connection({
    userName:  'test',
    password:  'test',
    server:    'localhost',
    options:  {
      database: 'mydb'
    }
  });
  const query = 'INSERT INTO dbo.Users SET Email = @Email, Password = @Password';
  connection.on('debug', function(text) {
    console.log(text);
  }).on('errorMessage', function(text) {
    console.log(JSON.stringify(text, null, 2));
  }).on('infoMessage', function(text) {
    console.log(JSON.stringify(text, null, 2));
  });
  connection.on('connect', function (err) {
    if (err) return callback(err);
    const request = new Request(query, function (err, rows) {
      if (err) return callback(err);
      callback(null);
    });
    bcrypt.hash(user.password, 10, function(err, hash) {
      if (err) return callback(err);
      request.addParameter('Email', TYPES.VarChar, user.email);
      request.addParameter('Password', TYPES.VarChar, hash);
      connection.execSql(request);
    });
  });
}
```

### Base de données SQL de Windows Azure

```javascript lines theme={null}
function create (user, callback) {
  //this example uses the "tedious" library
  //more info here: http://pekim.github.io/tedious/index.html
  var Connection = require('tedious@1.11.0').Connection;
  var Request = require('tedious@1.11.0').Request;
  var TYPES = require('tedious@1.11.0').TYPES;
  var bcrypt = require('bcrypt');
  var connection = new Connection({
    userName:  'your-user@your-server-id.database.windows.net',
    password:  'the-password',
    server:    'your-server-id.database.windows.net',
    options:  {
      database: 'mydb',
      encrypt:  true
    }
  });
  var query = "INSERT INTO users (Email, Password) VALUES (@Email, @Password)";
  connection.on('debug', function(text) {
    // Uncomment next line in order to enable debugging messages
    // console.log(text);
  }).on('errorMessage', function(text) {
    console.log(JSON.stringify(text, null, 2));
  }).on('infoMessage', function(text) {
    // Uncomment next line in order to enable information messages
    // console.log(JSON.stringify(text, null, 2));
  });
  connection.on('connect', function (err) {
    if (err) { return callback(err); }
    var request = new Request(query, function (err, rows) {
      if (err) { return callback(err); }
      console.log('rows: ' + rows);
      callback(null);
    });
    bcrypt.hash(user.password, 10, function (err, hashedPassword) {
      if (err) { return callback(err); }
      request.addParameter('Email', TYPES.VarChar, user.email);
      request.addParameter('Password', TYPES.VarChar, hashedPassword);
      connection.execSql(request);
    });
  });
}
```

### Demande avec Basic Auth

```javascript lines theme={null}
function create(user, callback) {
  const request = require('request');
  request.post({
    url: 'https://myserviceurl.com/users',
    json: user
    //for more options check:
    //https://github.com/mikeal/request#requestoptions-callback
  }, function(err, response, body) {
    if (err) return callback(err);
    callback(null);
  });
}
```

## Dépanner

Si vous ne parvenez pas à créer un utilisateur dans votre base de données héritée ou dans Auth0 :

1. Vérifiez les instructions `console.log()` avec l’[Journaux d'actions en temps réel](/docs/fr-ca/customize/actions/actions-real-time-logs) d’Auth0.
2. Recherchez l’utilisateur dans votre base de données héritée et supprimez-le. Si l’état utilisateur partiel est dans Auth0, utilisez les points de terminaison [Supprimer un utilisateur](https://auth0.com/docs/api/management/v2#!/Users/delete_users_by_id) ou [Supprimer un utilisateur de connexion](/docs/fr-ca/api/management/v2#!/Connections/delete_users_by_email) du Management API.
3. Assurez-vous que le **Mode d’importation** est désactivé, puis configurez le script de création.

## En savoir plus

* [Modèles de script de connexion](/docs/fr-ca/authenticate/database-connections/custom-db/templates/login)
* [Modèles de script Get User](/docs/fr-ca/authenticate/database-connections/custom-db/templates/get-user)
* [Modèles de script de suppression](/docs/fr-ca/authenticate/database-connections/custom-db/templates/delete)
* [Modèles de scripts Verify](/docs/fr-ca/authenticate/database-connections/custom-db/templates/verify)
* [Modifier les modèles de script de mot de passe](/docs/fr-ca/authenticate/database-connections/custom-db/templates/change-password)
* [Modifier le modèle de script de courriel](/docs/fr-ca/authenticate/database-connections/custom-db/templates/change-email)
