Adding client side check of setVariable with writableBy property

This commit is contained in:
David Négrier 2021-07-06 10:58:12 +02:00
parent 86fa869b20
commit cb78ff333b
5 changed files with 95 additions and 11 deletions

View file

@ -31,7 +31,7 @@ import {
EmoteEventMessage, EmoteEventMessage,
EmotePromptMessage, EmotePromptMessage,
SendUserMessage, SendUserMessage,
BanUserMessage, BanUserMessage, VariableMessage,
} from "../Messages/generated/messages_pb"; } from "../Messages/generated/messages_pb";
import type { UserSimplePeerInterface } from "../WebRtc/SimplePeer"; import type { UserSimplePeerInterface } from "../WebRtc/SimplePeer";
@ -536,6 +536,17 @@ export class RoomConnection implements RoomConnection {
this.socket.send(clientToServerMessage.serializeBinary().buffer); this.socket.send(clientToServerMessage.serializeBinary().buffer);
} }
emitSetVariableEvent(name: string, value: unknown): void {
const variableMessage = new VariableMessage();
variableMessage.setName(name);
variableMessage.setValue(JSON.stringify(value));
const clientToServerMessage = new ClientToServerMessage();
clientToServerMessage.setVariablemessage(variableMessage);
this.socket.send(clientToServerMessage.serializeBinary().buffer);
}
onActionableEvent(callback: (message: ItemEventMessageInterface) => void): void { onActionableEvent(callback: (message: ItemEventMessageInterface) => void): void {
this.onMessage(EventMessage.ITEM_EVENT, (message: ItemEventMessage) => { this.onMessage(EventMessage.ITEM_EVENT, (message: ItemEventMessage) => {
callback({ callback({

View file

@ -9,7 +9,9 @@ import type {ITile, ITiledMapObject} from "../Map/ITiledMap";
import type {Var} from "svelte/types/compiler/interfaces"; import type {Var} from "svelte/types/compiler/interfaces";
interface Variable { interface Variable {
defaultValue: unknown defaultValue: unknown,
readableBy?: string,
writableBy?: string,
} }
export class SharedVariablesManager { export class SharedVariablesManager {
@ -30,15 +32,24 @@ export class SharedVariablesManager {
iframeListener.registerAnswerer('setVariable', (event) => { iframeListener.registerAnswerer('setVariable', (event) => {
const key = event.key; const key = event.key;
if (!this.variableObjects.has(key)) { const object = this.variableObjects.get(key);
if (object === undefined) {
const errMsg = 'A script is trying to modify variable "'+key+'" but this variable is not defined in the map.' + const errMsg = 'A script is trying to modify variable "'+key+'" but this variable is not defined in the map.' +
'There should be an object in the map whose name is "'+key+'" and whose type is "variable"'; 'There should be an object in the map whose name is "'+key+'" and whose type is "variable"';
console.error(errMsg); console.error(errMsg);
throw new Error(errMsg); throw new Error(errMsg);
} }
if (object.writableBy && !this.roomConnection.hasTag(object.writableBy)) {
const errMsg = 'A script is trying to modify variable "'+key+'" but this variable is only writable for users with tag "'+object.writableBy+'".';
console.error(errMsg);
throw new Error(errMsg);
}
this._variables.set(key, event.value); this._variables.set(key, event.value);
// TODO: dispatch to the room connection. // TODO: dispatch to the room connection.
this.roomConnection.emitSetVariableEvent(key, event.value);
}); });
} }
@ -68,8 +79,27 @@ export class SharedVariablesManager {
if (object.properties) { if (object.properties) {
for (const property of object.properties) { for (const property of object.properties) {
if (property.name === 'default') { const value = property.value;
variable.defaultValue = property.value; switch (property.name) {
case 'default':
variable.defaultValue = value;
break;
case 'writableBy':
if (typeof value !== 'string') {
throw new Error('The writableBy property of variable "'+object.name+'" must be a string');
}
if (value) {
variable.writableBy = value;
}
break;
case 'readableBy':
if (typeof value !== 'string') {
throw new Error('The readableBy property of variable "'+object.name+'" must be a string');
}
if (value) {
variable.readableBy = value;
}
break;
} }
} }
} }

View file

@ -7,9 +7,14 @@ WA.onInit().then(() => {
console.log('Successfully caught error: ', e); console.log('Successfully caught error: ', e);
}); });
console.log('Trying to set variable "config". This should work.'); console.log('Trying to set variable "myvar". This should work.');
WA.room.saveVariable('config', {'foo': 'bar'}); WA.room.saveVariable('myvar', {'foo': 'bar'});
console.log('Trying to read variable "config". This should display a {"foo": "bar"} object.'); console.log('Trying to read variable "myvar". This should display a {"foo": "bar"} object.');
console.log(WA.room.loadVariable('config')); console.log(WA.room.loadVariable('myvar'));
console.log('Trying to set variable "config". This should not work because we are not logged as admin.');
WA.room.saveVariable('config', {'foo': 'bar'}).catch(e => {
console.log('Successfully caught error because variable "config" is not writable: ', e);
});
}); });

View file

@ -104,6 +104,44 @@
"width":0, "width":0,
"x":131.38069962269, "x":131.38069962269,
"y":106.004988169086 "y":106.004988169086
},
{
"height":0,
"id":9,
"name":"myvar",
"point":true,
"properties":[
{
"name":"default",
"type":"string",
"value":"{}"
},
{
"name":"jsonSchema",
"type":"string",
"value":"{}"
},
{
"name":"persist",
"type":"bool",
"value":true
},
{
"name":"readableBy",
"type":"string",
"value":""
},
{
"name":"writableBy",
"type":"string",
"value":""
}],
"rotation":0,
"type":"variable",
"visible":true,
"width":0,
"x":88.8149900876127,
"y":147.75212636695
}], }],
"opacity":1, "opacity":1,
"type":"objectgroup", "type":"objectgroup",
@ -112,7 +150,7 @@
"y":0 "y":0
}], }],
"nextlayerid":8, "nextlayerid":8,
"nextobjectid":9, "nextobjectid":10,
"orientation":"orthogonal", "orientation":"orthogonal",
"properties":[ "properties":[
{ {

View file

@ -186,7 +186,7 @@ message RoomJoinedMessage {
repeated ItemStateMessage item = 3; repeated ItemStateMessage item = 3;
int32 currentUserId = 4; int32 currentUserId = 4;
repeated string tag = 5; repeated string tag = 5;
repeated VariableMessage = 6; repeated VariableMessage variable = 6;
} }
message WebRtcStartMessage { message WebRtcStartMessage {