Les requêtes que vous effectuez vers les magasins de données peuvent échouer en raison d'une mauvaise connectivité ou d'autres problèmes. Pour gérer les erreurs et renvoyer des messages avec un code d'erreur, enveloppez les fonctions de magasin de données dans pcall().
Un appel d'écriture échoué, tel que UpdateAsync(), signifie que le serveur de jeu n'a pas reçu de réponse réussie. Cela ne garantit pas toujours que l'écriture en arrière-plan n'a pas eu lieu. Dans certains scénarios d'échec, l'état final de l'écriture peut être inconnu pour l'appelant jusqu'à ce qu'il soit vérifié avec une lecture de suivi sans cache.
Référence des codes d'erreur
| Code d'erreur | Nom de l'erreur | Message d'erreur | Remarques | |
|---|---|---|---|---|
| 101 | KeyNameEmpty | Le nom de la clé ne peut pas être vide. | Vérifiez si la clé saisie dans la fonction de magasin de données est une chaîne vide. | |
| 102 | KeyNameLimit | Le nom de la clé dépasse la limite de 50 caractères. | Vérifiez si la clé saisie dans la fonction de magasin de données dépasse une longueur de 50. | |
| 103 | ValueNotAllowed | Impossible d'autoriser X dans DataStore. | Une mauvaise fonction de mise à jour a renvoyé une valeur de type X. | |
| 104 | CantStoreValue | Impossible de stocker X dans DataStore. | La fonction de mise à jour a renvoyé une valeur de type X qui n'a pas pu être sérialisée. | |
| 105 | ValueTooLarge | La valeur sérialisée dépasse la limite de X. | Si vous définissez une valeur avec SetAsync() ou UpdateAsync(), la longueur sérialisée de la valeur ne peut pas dépasser la taille X. Pour vérifier la longueur sérialisée des données, utilisez JSONEncode(). | |
| 106 | MaxValueInvalid | MaxValue doit être un entier. | Si vous passez une valeur maximale à GetSortedAsync() pour un OrderedDataStore, cela doit être un entier. | |
| 106 | MinValueInvalid | MinValue doit être un entier. | Si vous passez une valeur minimale à GetSortedAsync() pour un OrderedDataStore, cela doit être un entier. | |
| 106 | PageSizeGreater | PageSize doit être dans une plage prédéfinie. | La taille de page minimale pour un OrderedDataStore est 1. | |
| 106 | PageSizeLesser | PageSize doit être dans une plage prédéfinie. | La taille de page maximale pour un OrderedDataStore est 100. | |
| 107 | MinMaxOrderInvalid | MaxValue doit être supérieur ou égal à MinValue. | La valeur maximale doit être supérieure ou égale à la valeur minimale pour GetSortedAsync(). | |
| 301 | GetAsyncThrottle | Requête GetAsync abandonnée. La requête a été limitée mais la file d'attente était pleine. | La requête GetAsync() a dépassé la taille maximale de la file d'attente et Roblox ne peut pas traiter les requêtes au débit actuel. | |
| 302 | SetAsyncThrottle | Requête SetAsync abandonnée. La requête a été limitée mais la file d'attente était pleine. | La requête SetAsync() a dépassé la taille maximale de la file d'attente et Roblox ne peut pas traiter les requêtes au débit actuel. | |
| 303 | IncreAsyncThrottle | Requête IncrementAsync abandonnée. La requête a été limitée mais la file d'attente était pleine. | La requête IncrementAsync() a dépassé la taille maximale de la file d'attente et Roblox ne peut pas traiter les requêtes au débit actuel. | |
| 304 | UpdateAsyncThrottle | Requête UpdateAsync abandonnée. La requête a été limitée mais la file d'attente était pleine. | La requête UpdateAsync() a dépassé la taille maximale de la file d'attente et Roblox ne peut pas traiter les requêtes au débit actuel. | |
| 304 | TransformThrottle | Requête UpdateAsync abandonnée. La requête a été limitée mais la file d'attente était pleine. | La requête UpdateAsync() a dépassé la taille maximale de la file d'attente et Roblox ne peut pas traiter les requêtes au débit actuel. | |
| 305 | GetSortedThrottle | Requête GetSorted abandonnée. La requête a été limitée mais la file d'attente était pleine. | La requête GetSortedAsync() a dépassé la taille maximale de la file d'attente et Roblox ne peut pas traiter les requêtes au débit actuel. | |
| 306 | RemoveAsyncThrottle | Requête RemoveAsync abandonnée. La requête a été limitée mais la file d'attente était pleine. | La requête RemoveAsync() a dépassé la taille maximale de la file d'attente et Roblox ne peut pas traiter les requêtes au débit actuel. | |
| 401 | DataModelNoAccess | La requête a échoué. DataModel est inaccessible pendant que l'expérience est en cours d'arrêt. | DataModel n'est pas initialisé car l'expérience est en cours d'arrêt. | |
| 402 | LuaWebSrvsNoAccess | La requête a échoué. LuaWebService est inaccessible pendant que l'expérience est en cours d'arrêt. | LuaWebService n'est pas initialisé car l'expérience est en cours d'arrêt. | |
| 403 | StudioAccessToApisNotAllowed | Impossible d'écrire dans DataStore depuis Studio car l'accès à l'API n'est pas activé. | L'accès à l'API doit être actif pour utiliser les magasins de données dans Studio. | |
| 404 | InternalError | OrderedDataStore n'existe pas. | Le OrderedDataStore associé à cette requête n'a pas été trouvé. Cela pourrait être un signe de corruption des données. Réessayez plus tard. | |
| 501 | InternalError | Impossible d'analyser la réponse car les données pourraient être corrompues. | Le serveur n'a pas pu analyser la réponse à votre requête. Cela pourrait être un signe de corruption des données. Réessayez plus tard. | |
| 502 | RequestRejected | Les services API ont rejeté la requête avec l'erreur X. | Une erreur X s'est produite lors du traitement sur les serveurs Roblox. Réessayez plus tard. | |
| 503 | InternalError | La requête de magasin de données a réussi mais la clé n'a pas été trouvée. | La clé demandée n'a pas été trouvée dans le magasin de données. Cela pourrait être un signe de corruption des données. Réessayez plus tard. | |
| 504 | InternalError | La requête de magasin de données a réussi mais la réponse n'était pas correctement formatée. | Le serveur n'a pas pu analyser la réponse à votre requête. Cela pourrait être un signe de corruption des données. Réessayez plus tard. | |
| 505 | InternalError | La requête OrderedDataStore a réussi mais la réponse n'était pas correctement formatée. | Le serveur n'a pas pu analyser la réponse à votre requête OrderedDataStore. Cela pourrait être un signe de corruption des données. Réessayez plus tard. | |
| 509 | OperationNotAllowed | Les opérations de magasin de données sont bloquées lors de l'exécution sur un RCC personnel pour éviter une possible corruption des données. | Les écritures dans le magasin de données sont bloquées sur les canaux RCC privés. | |
| 511 | AttributeSizeTooLarge | La taille de l'attribut de métadonnées dépasse la limite de X. | La taille des métadonnées sérialisées dépasse la limite de X. La valeur X est dynamique. Si la taille change, la valeur change également. | |
| 512 | UserIdLimitExceeded | La taille de UserID dépasse la limite de X. | La longueur du tableau d'ID utilisateur fourni par l'utilisateur dépasse la limite de X. | |
| 513 | AttributeFormatError | Le format de l'attribut userId est invalide. | L'ID utilisateur fourni n'est pas un nombre. | |
| 513 | AttributeFormatError | Le format des métadonnées d'attribut est invalide. | Les métadonnées ne sont pas un tableau. | |
| GetVersionAsyncThrottle | Requête GetVersionAsync abandonnée. La requête a été limitée. | La requête GetVersionAsync() a dépassé la taille maximale de la file d'attente et Roblox ne peut pas traiter les requêtes au débit actuel. | ||
| GetVersionAtTimeAsyncThrottle | Requête GetVersionAtTimeAsync abandonnée. La requête a été limitée. | La requête GetVersionAtTimeAsync() a dépassé la taille maximale de la file d'attente et Roblox ne peut pas traiter les requêtes au débit actuel. | ||
| ListDataStoresAsyncThrottle | Requête ListDataStoresAsync abandonnée. La requête a été limitée. | La requête ListDataStoresAsync() a dépassé la taille maximale de la file d'attente et Roblox ne peut pas traiter les requêtes au débit actuel. | ||
| ListKeysAsyncThrottle | Requête ListKeysAsync abandonnée. La requête a été limitée. | La requête ListKeysAsync() a dépassé la taille maximale de la file d'attente et Roblox ne peut pas traiter les requêtes au débit actuel. | ||
| ListVersionsAsyncThrottle | Requête ListVersionsAsync abandonnée. La requête a été limitée. | La requête ListVersionsAsync() a dépassé la taille maximale de la file d'attente et Roblox ne peut pas traiter les requêtes au débit actuel. | ||
| RemoveVersionAsyncThrottle | Requête RemoveVersionAsync abandonnée. La requête a été limitée. | La requête RemoveVersionAsync() a dépassé la taille maximale de la file d'attente et Roblox ne peut pas traiter les requêtes au débit actuel. | ||
| InvalidTimestamp | Le timestamp doit être positif et ne pas dépasser dix minutes dans le futur. | Le timestamp fourni à GetVersionAtTimeAsync() n'était pas valide. | ||
| StandardReadExperienceThrottled | La requête StandardRead a été limitée par les limites d'expérience. | Une requête à GetAsync(), GetVersionAsync(), GetVersionAtTimeAsync(), ou la lecture de UpdateAsync() sur un magasin de données standard a dépassé la limite de taux d'expérience StandardRead. | ||
| StandardWriteExperienceThrottled | La requête StandardWrite a été limitée par les limites d'expérience. | Une requête à SetAsync(), IncrementAsync(), ou l'écriture de UpdateAsync() sur un magasin de données standard a dépassé la limite de taux d'expérience StandardWrite. | ||
| StandardListExperienceThrottled | La requête StandardList a été limitée par les limites d'expérience. | Une requête à ListKeysAsync(), ListVersionsAsync(), ou ListDataStoresAsync() sur des magasins de données standard a dépassé la limite de taux d'expérience StandardList. | ||
| StandardRemoveExperienceThrottled | La requête StandardRemove a été limitée par les limites d'expérience. | Une requête à RemoveAsync() sur un magasin de données standard a dépassé la limite de taux d'expérience StandardRemove. | ||
| OrderedReadExperienceThrottled | La requête OrderedRead a été limitée par les limites d'expérience. | Une requête à GetAsync(), BatchGetAsync(), ou la lecture de UpdateAsync() sur un magasin de données ordonné a dépassé la limite de taux d'expérience OrderedRead. | ||
| OrderedWriteExperienceThrottled | La requête OrderedWrite a été limitée par les limites d'expérience. | Une requête à SetAsync(), IncrementAsync(), ou l'écriture de UpdateAsync() sur un magasin de données ordonné a dépassé la limite de taux d'expérience OrderedWrite. | ||
| OrderedListExperienceThrottled | La requête OrderedList a été limitée par les limites d'expérience. | Une requête à GetSortedAsync() sur un magasin de données ordonné a dépassé la limite de taux d'expérience OrderedList. | ||
| OrderedRemoveExperienceThrottled | La requête OrderedRemove a été limitée par les limites d'expérience. | Une requête à RemoveAsync() sur un magasin de données ordonné a dépassé la limite de taux d'expérience OrderedRemove. | ||
| StandardReadGameServerThrottled | La requête StandardRead a été limitée par les limites du serveur de jeu ou la file d'attente des requêtes était pleine. | Une requête à GetAsync(), GetVersionAsync(), GetVersionAtTimeAsync(), ou la lecture de UpdateAsync() sur un magasin de données standard a dépassé la limite de taux du serveur de jeu StandardRead. | ||
| StandardWriteGameServerThrottled | La requête StandardWrite a été limitée par les limites du serveur de jeu ou la file d'attente des requêtes était pleine. | Une requête à SetAsync(), IncrementAsync(), ou l'écriture de UpdateAsync() sur un magasin de données standard a dépassé la limite de taux du serveur de jeu StandardWrite. | ||
| StandardListGameServerThrottled | La requête StandardList a été limitée par les limites du serveur de jeu ou la file d'attente des requêtes était pleine. | Une requête à ListKeysAsync(), ListVersionsAsync(), ou ListDataStoresAsync() sur des magasins de données standard a dépassé la limite de taux du serveur de jeu StandardList. | ||
| StandardRemoveGameServerThrottled | La requête StandardRemove a été limitée par les limites du serveur de jeu ou la file d'attente des requêtes était pleine. | Une requête à RemoveAsync() sur un magasin de données standard a dépassé la limite de taux du serveur de jeu StandardRemove. | ||
| OrderedReadGameServerThrottled | La requête OrderedRead a été limitée par les limites du serveur de jeu ou la file d'attente des requêtes était pleine. | Une requête à GetAsync(), BatchGetAsync(), ou la lecture de UpdateAsync() sur un magasin de données ordonné a dépassé la limite de taux du serveur de jeu OrderedRead. | ||
| OrderedWriteGameServerThrottled | La requête OrderedWrite a été limitée par les limites du serveur de jeu ou la file d'attente des requêtes était pleine. | Une requête à SetAsync(), IncrementAsync(), ou l'écriture de UpdateAsync() sur un magasin de données ordonné a dépassé la limite de taux du serveur de jeu OrderedWrite. | ||
| OrderedListGameServerThrottled | La requête OrderedList a été limitée par les limites du serveur de jeu ou la file d'attente des requêtes était pleine. | Une requête à GetSortedAsync() sur un magasin de données ordonné a dépassé la limite de taux du serveur de jeu OrderedList. | ||
| OrderedRemoveGameServerThrottled | La requête OrderedRemove a été limitée par les limites du serveur de jeu ou la file d'attente des requêtes était pleine. | Une requête à RemoveAsync() sur un magasin de données ordonné a dépassé la limite de taux du serveur de jeu OrderedRemove. |
Codes d'erreur du serveur
| Nom de l'erreur | Message d'erreur | Remarques |
|---|---|---|
| DatastoreDeleted | Le magasin de données est supprimé. | Une opération sur le magasin de données n'a pas pu se produire car le magasin de données a été précédemment supprimé. |
| DatastoreThrottled | Le taux de requêtes dépasse le maximum autorisé pour le datastore. | Trop de requêtes ont été envoyées à un seul magasin de données. |
| InternalServerError | Une erreur interne du serveur s'est produite. | Erreur occasionnelle sur les serveurs Roblox. Réessayez, idéalement avec un retour exponentiel. |
| InvalidExclusiveStartKey | La clé de départ exclusive fournie n'est pas valide. | La clé de départ exclusive (curseur) fournie à une opération de liste telle que ListKeysAsync() n'est pas valide. |
| InvalidPlace | Le lieu fourni est invalide. | Aucun ID d'univers correspondant pour le lieu. Réessayez plus tard. |
| InvalidTarget | La cible fournie est invalide. | Le nom de la clé du magasin de données ordonné dépasse la limite de 50 caractères. |
| InvalidUniverse | L'univers fourni est invalide. | Aucun ID de lieu correspondant pour l'univers. Réessayez plus tard. |
| InvalidUserIds | Les ID utilisateur fournis ont un format invalide. | Échec de l'analyse des ID utilisateur. |
| KeyThrottled | Le taux de requêtes dépasse le maximum autorisé pour la clé. | Le taux de requêtes dépasse le taux de requêtes maximum autorisé pour une seule clé. |
| KeyNotFound | La clé demandée n'existe pas. | La clé n'existe pas. |
| N/A | Aucune page à avancer. | Cette erreur se produit lorsque vous appelez Pages:AdvanceToNextPageAsync() sur la dernière page. |
| StandardReadExperienceThrottled | Le taux de requêtes de lecture standard dépasse le maximum autorisé pour l'expérience. | Une requête à GetAsync(), GetVersionAsync(), GetVersionAtTimeAsync(), ou la lecture de UpdateAsync() sur un magasin de données standard a dépassé la limite de taux d'expérience StandardRead. |
| StandardWriteExperienceThrottled | Le taux de requêtes d'écriture standard dépasse le maximum autorisé pour l'expérience. | Une requête à SetAsync(), IncrementAsync(), ou l'écriture de UpdateAsync() sur un magasin de données standard a dépassé la limite de taux d'expérience StandardWrite. |
| StandardListExperienceThrottled | Le taux de requêtes de liste standard dépasse le maximum autorisé pour l'expérience. | Une requête à ListKeysAsync(), ListVersionsAsync(), ou ListDataStoresAsync() sur des magasins de données standard a dépassé la limite de taux d'expérience StandardList. |
| StandardRemoveExperienceThrottled | Le taux de requêtes de suppression standard dépasse le maximum autorisé pour l'expérience. | Une requête à RemoveAsync() sur un magasin de données standard a dépassé la limite de taux d'expérience StandardRemove. |
| OrderedReadExperienceThrottled | Le taux de requêtes de lecture ordonnée dépasse le maximum autorisé pour l'expérience. | Une requête à GetAsync(), BatchGetAsync(), ou la lecture de UpdateAsync() sur un magasin de données ordonné a dépassé la limite de taux d'expérience OrderedRead. |
| OrderedWriteExperienceThrottled | Le taux de requêtes d'écriture ordonnée dépasse le maximum autorisé pour l'expérience. | Une requête à SetAsync(), IncrementAsync(), ou l'écriture de UpdateAsync() sur un magasin de données ordonné a dépassé la limite de taux d'expérience OrderedWrite. |
| OrderedListExperienceThrottled | Le taux de requêtes de liste ordonnée dépasse le maximum autorisé pour l'expérience. | Une requête à GetSortedAsync() sur un magasin de données ordonné a dépassé la limite de taux d'expérience OrderedList. |
| OrderedRemoveExperienceThrottled | Le taux de requêtes de suppression ordonnée dépasse le maximum autorisé pour l'expérience. | Une requête à RemoveAsync() sur un magasin de données ordonné a dépassé la limite de taux d'expérience OrderedRemove. |
Limites
Les modèles de données ont des limites. Si une expérience dépasse ces limites, le service limite automatiquement l'utilisation du magasin de données de l'expérience et place les futures requêtes dans l'une des files d'attente suivantes :
- Définir
- Définir ordonné
- Obtenir
- Obtenir ordonné
Les requêtes dans une file d'attente sont traitées dans l'ordre dans lequel elles sont reçues. La fonction appelée continue de céder tant que sa requête est toujours en file d'attente. Si la clé du magasin de données elle-même est limitée, la requête est placée dans une file d'attente mais est temporairement ignorée.
Chaque file d'attente a une limite de 30 requêtes. Lorsque la limite d'une file d'attente est atteinte, les requêtes échouent avec un code d'erreur dans la plage 301-306, indiquant que les requêtes ont été complètement abandonnées.
Limites d'accès
Les magasins de données sont soumis à la fois à des limites d'expérience et de serveur. Les limites de niveau d'expérience évoluent avec le nombre total d'utilisateurs simultanés dans l'expérience, tandis que les limites de niveau de serveur sont configurables et destinées à être utilisées comme un outil par le créateur.
Limites d'expérience
Chaque expérience est autorisée à un certain nombre de requêtes de magasin de données en fonction du type de magasin de données, du type de requête et du nombre d'utilisateurs simultanés. Pour chaque type de magasin de données et type de requête, la limite est partagée entre toutes les fonctions répertoriées.
- UpdateAsync() consomme à la fois le budget de requêtes de lecture et d'écriture. Un seul appel diminuera les deux limites.
- Le serveur de jeu et Open Cloud partagent un budget ; le trafic Open Cloud peut être limité par l'utilisation dans l'expérience (et vice versa). Voir Contrôler les limites de taux pour plus de conseils.
Magasins de données standard
| Type de requête | API du serveur de jeu | API Open Cloud | Limites partagées (requêtes par minute) |
|---|---|---|---|
| Lecture | GetAsync() GetVersionAsync() GetVersionAtTimeAsync() UpdateAsync() | Obtenir l'entrée du magasin de données | 300 + utilisateursSimultanés × 40 |
| Écriture | SetAsync() IncrementAsync() UpdateAsync() | Créer, Mettre à jour, Incrémenter l'entrée du magasin de données | 300 + utilisateursSimultanés × 20 |
| Liste | ListDataStoresAsync() ListKeysAsync() ListVersionsAsync() | Lister les magasins de données, Lister les entrées de magasin de données, Lister les révisions d'entrée de magasin de données | 300 + utilisateursSimultanés × 2 |
| Suppression | RemoveAsync() | Supprimer l'entrée du magasin de données, Supprimer le magasin de données, Récupérer le magasin de données | 300 + utilisateursSimultanés × 40 |
Magasins de données ordonnés
| Type de requête | API du serveur de jeu | API Open Cloud | Limites partagées (requêtes par minute) |
|---|---|---|---|
| Lecture | GetAsync() BatchGetAsync() UpdateAsync() | Obtenir l'entrée du magasin de données ordonné | 300 + utilisateursSimultanés × 40 |
| Écriture | SetAsync() IncrementAsync() UpdateAsync() | Créer, Mettre à jour, Incrémenter l'entrée du magasin de données ordonné | 300 + utilisateursSimultanés × 20 |
| Liste | GetSortedAsync() | Lister les entrées du magasin de données ordonné | 300 + utilisateursSimultanés × 2 |
| Suppression | RemoveAsync() | Supprimer l'entrée du magasin de données ordonné | 300 + utilisateursSimultanés × 40 |
Contrôler les limites de taux
Parce que les requêtes Open Cloud et serveur de jeu sont partagées, il est important de contrôler indépendamment combien chacune peut consommer du budget.
Serveur de jeu
Les serveurs individuels ont des limites intégrées, comme décrit ci-dessus. Utilisez une combinaison de SetRateLimitForRequestType() et GetRequestBudgetForRequestType() pour maintenir un contrôle précis sur la contribution des serveurs individuels au budget total.
Open Cloud
Les requêtes Open Cloud nécessitent une solution de limitation de taux externe. Nous recommandons l'une des approches suivantes :
- (Simple) Ajoutez un court délai après chaque requête, surtout si vous appelez la même API dans une boucle continue. Définissez ce délai égal à 60 / (consommation de budget souhaitée par minute) secondes, comme une limite supérieure. Notez que cette approche ne permet pas d'envoyer des requêtes en rafales.
- (Robuste) Implémentez un limiteur de taux local en utilisant la stratégie du seau qui fuit.
Les exemples de code Node.js suivants incluent des implémentations de référence.
const apiKey = process.env.API_KEY;
if (!apiKey) {
throw new Error('La variable d\'environnement API_KEY n\'est pas définie.');
}
const apiHeaderKey = 'x-api-key';
const universeId = '';
const dataStoreId = 'Inventory';
const baseUrl = 'https://apis.roblox.com/cloud/v2/';
// --- Configuration de limitation de taux par opération (requêtes par minute) ---
const LIST_RATE_PER_MIN = 60;
const GET_RATE_PER_MIN = 120;
const UPDATE_RATE_PER_MIN = 60;
// Espacement maximal par opération : 60 / (requêtes par min) secondes.
const LIST_INTERVAL_MS = (60 / LIST_RATE_PER_MIN) * 1000;
const GET_INTERVAL_MS = (60 / GET_RATE_PER_MIN) * 1000;
const UPDATE_INTERVAL_MS = (60 / UPDATE_RATE_PER_MIN) * 1000;
const sleep = (ms) => new Promise((resolve) => setTimeout(resolve, ms));
// Effectue la requête, puis attend l'intervalle de cette opération avant de retourner.
async function throttledFetch(url, options, intervalMs) {
const response = await fetch(url, options);
await sleep(intervalMs);
return response;
}
async function listEntries(universe, dataStore) {
const listPath = `universes/${universe}/data-stores/${dataStore}/entries`;
const url = baseUrl + listPath;
const response = await throttledFetch(url, {
headers: { [apiHeaderKey]: apiKey }
}, LIST_INTERVAL_MS);
return response.json();
}
async function getEntry(path) {
const url = baseUrl + path;
const response = await throttledFetch(url, {
headers: { [apiHeaderKey]: apiKey }
}, GET_INTERVAL_MS);
return response.json();
}
async function updateEntry(path, payload) {
const url = baseUrl + path;
const response = await throttledFetch(url, {
method: 'PATCH',
headers: {
[apiHeaderKey]: apiKey,
'Content-Type': 'application/json'
},
body: JSON.stringify(payload) // Le corps doit être une chaîne
}, UPDATE_INTERVAL_MS);
return response;
}
(async () => {
try {
const entries = await listEntries(universeId, dataStoreId);
for (const entry of entries.dataStoreEntries) {
const path = entry.path;
console.log(`\nTraitement de l'entrée : ${path}`);
const currentData = await getEntry(path);
currentData.value.currency += 10;
const payload = { value: currentData.value };
const updateResponse = await updateEntry(path, payload);
console.log(`Statut : ${updateResponse.status}`);
console.log(`Réponse : ${await updateResponse.text()}`);
}
} catch (error) {
console.error('Une erreur s\'est produite pendant l\'exécution :', error);
}
})();Limites du serveur
Chaque serveur a une limite de taux configurable pour chaque type de requête, basée sur le nombre de joueurs dans ce serveur. Les serveurs reçoivent une rafale de budget de requêtes supplémentaire lors de leur première création. Utilisez GetRequestBudgetForRequestType() pour confirmer le nombre de requêtes de magasin de données que le serveur actuel peut effectuer à tout moment.
Ces limites sont configurables par le créateur en utilisant l'API SetRateLimitForRequestType(). En utilisant cette API, un créateur peut configurer ses propres limites de taux de magasins de données pour chaque type de requête.
Les limites de taux par défaut suivantes s'appliquent si l'API n'est pas appelée :
Magasins de données standard
| Type de requête | Enum DataStoreRequestType | API du serveur de jeu | Requêtes par minute |
|---|---|---|---|
| Lecture | StandardRead | GetAsync() GetVersionAsync() GetVersionAtTimeAsync() UpdateAsync() | 60 + numPlayers × 40 |
| Écriture | StandardWrite | SetAsync() IncrementAsync() UpdateAsync() | 60 + numPlayers × 40 |
| Liste | StandardList | ListDataStoresAsync() ListKeysAsync() ListVersionsAsync() | 5 + numPlayers × 2 |
| Suppression | StandardRemove | RemoveAsync() | 60 + numPlayers × 40 |
| RemoveVersion (Déprécié) | RemoveVersionAsync | RemoveVersionAsync() | 5 + numPlayers × 2 |
Magasins de données ordonnés
| Type de requête | Enum DataStoreRequestType | API du serveur de jeu | Requêtes par minute |
|---|---|---|---|
| Lecture | OrderedRead | GetAsync() BatchGetAsync() UpdateAsync() | 60 + numPlayers × 40 |
| Écriture | OrderedWrite | SetAsync() IncrementAsync() UpdateAsync() | 30 + numPlayers × 5 |
| Liste | OrderedList | GetSortedAsync() | 5 + numPlayers × 2 |
| Suppression | OrderedRemove | RemoveAsync() | 30 + numPlayers × 5 |
Limites de données
Les magasins de données limitent la quantité de données pouvant être utilisées par entrée.
Le nom du magasin de données, le nom de la clé et le scope doivent tous être sous une certaine longueur de caractères. Utilisez string.len() pour vérifier leur longueur.
Les données (valeur de clé) sont également stockées sous forme de chaîne, quel que soit leur type initial. Vous pouvez vérifier la taille des données avec la fonction JSONEncode(), qui convertit les données Luau en une table JSON sérialisée.
| Composant | Nombre maximum de caractères |
|---|---|
| Nom du magasin de données | 50 |
| Nom de la clé | 50 |
| Scope | 50 |
| Données (valeur de clé) | 4,194,304 par clé |
Limites de métadonnées
Limites au nombre de caractères dans les métadonnées définies par l'utilisateur.
| Composant | Nombre maximum de caractères |
|---|---|
| Nom de la clé | 50 |
| Valeur | 250 |
| Paires clé-valeur | 300 |
Limites de débit
Les limites de débit par clé garantissent que les performances sont optimales sur les serveurs Roblox. Chaque limite s'applique à chaque clé unique sur tous les serveurs d'une expérience et se rafraîchit au fil du temps.
Roblox examine l'utilisation du quota associé à la clé au cours des 60 dernières secondes. Si l'utilisation, y compris la requête actuelle, est dans la limite de débit, la requête est approuvée. Si l'utilisation dépasse la limite, la requête est refusée.
| Type de requête | API du serveur de jeu | API Open Cloud | Limite |
|---|---|---|---|
| Lecture | GetAsync() GetVersionAsync() GetVersionAtTimeAsync() ListVersionsAsync() UpdateAsync() | Obtenir l'entrée du magasin de données | 25 Mo par minute |
| Écriture | SetAsync() IncrementAsync() UpdateAsync() RemoveAsync() | Créer, Mettre à jour, Incrémenter, Supprimer l'entrée du magasin de données | 4 Mo par minute |
En plus des limites de débit ci-dessus, Roblox organise les données en partitions basées sur un schéma interne. En conséquence, lorsque le serveur arrière reçoit un volume élevé de requêtes vers le même magasin de données, cela peut entraîner un throttling supplémentaire. Quelle qu'en soit la cause, le throttling se manifeste par des erreurs DatastoreThrottled ou KeyThrottled, selon que la limite de débit a été dépassée pour un magasin de données unique ou une clé. Ces messages d'erreur s'appliquent à la fois aux magasins de données ordonnés et standard.
Limites de stockage
Pour maintenir un stockage stable et évolutif, les magasins de données utilisent une limite de niveau de jeu sur votre utilisation de stockage.
Cette limite se compose d'une allocation de base pour chaque jeu plus une allocation supplémentaire basée sur le nombre d'utilisateurs à vie. Un utilisateur à vie est tout utilisateur qui a rejoint votre jeu au moins une fois.
La limite de stockage est calculée en utilisant la formule suivante Limite de stockage de la dernière version totale = 500 Mo + 1 Mo × nombre d'utilisateurs à vie.
L'utilisation du stockage est mesurée en utilisant la taille compressée de la dernière version de chaque clé. Les magasins de données compressent automatiquement vos données avant le stockage, donc évitez de les compresser vous-même. La pré-compression ajoute une surcharge CPU inutile et peut réduire l'efficacité de la compression intégrée des magasins de données. En stockant des données non compressées, vous bénéficiez automatiquement des améliorations des algorithmes de compression de Roblox et des optimisations basées sur le schéma à venir.
Seule la dernière version de chaque clé compte pour votre utilisation de stockage. Les clés supprimées et les versions remplacées, bien qu'encore accessibles via les API de version pendant leur période de conservation, ne comptent pas pour votre utilisation de stockage. Cependant, les magasins de données supprimés via la méthode Open Cloud DeleteDataStore continuent de compter pour l'utilisation de stockage pendant leur période de traitement de suppression de 30 jours, jusqu'à ce qu'ils soient définitivement supprimés.