-
Notifications
You must be signed in to change notification settings - Fork 5
Entity Class
Entity classes in PHP work just like PHP objects. In JavaScript, the same is mostly true, but instance methods begin with a $
character, since JavaScript method names can collide with property names.
In JavaScript, assigning a property internally marks that property as "dirty", and calling $patch
will push just the changed properties up to the server, whereas $save
would push all properties.
Entities can be organized using tags. To add, remove, and check tags, the methods addTag
, removeTag
, and hasTag
are used, respectively. Each takes any number of tags or an array of tags as arguments.
$entity = MyEntityClass::factory();
$entity->addTag('foo', 'bar');
$entity->hasTag('foo'); // True
$entity->removeTag('foo', 'bar');
$entity->hasTag('foo'); // False
let entity = new MyEntityClass();
entity.$addTag('foo', 'bar');
entity.$hasTag('foo'); // True
entity.$removeTag('foo', 'bar');
entity.$hasTag('foo'); // False
To clear the cache of referenced entities, so that the next time one is accessed it will be pulled from the database, use the clearCache
method in PHP and the $refresh
method in JavaScript.
$entity = MyEntityClass::factory();
$entity->foo = MyEntityClass::factory();
$entity->foo->bar = 'Old value.';
$entity->foo->save();
$entity->save();
$entity = \Nymph\Nymph::getEntity(['class' => 'MyEntityClass'], ['&', 'guid' => $entity->guid]);
$instOfFoo = \Nymph\Nymph::getEntity(['class' => 'MyEntityClass'], ['&', 'guid' => $entity->foo->guid]);
$instOfFoo->bar = 'New value.';
$instOfFoo->save();
echo $entity->foo->bar; // Outputs 'Old value.'
$entity->clearCache();
echo $entity->foo->bar; // Outputs 'New value.'
let entity = new MyEntityClass();
entity.foo = new MyEntityClass();
entity.foo.bar = 'Old value.';
await entity.foo.$save();
await entity.$save();
entity = await Nymph.getEntity({'class': MyEntityClass.class}, {'type': '&', 'guid': entity.guid});
let instOfFoo = await Nymph.getEntity({'class' => MyEntityClass.class}, {'type': '&', 'guid': entity.foo.guid});
instOfFoo.bar = 'New value.';
await instOfFoo.$save();
console.log(entity.foo.bar); // Outputs 'Old value.'
await entity.$refresh();
await entity.foo.$ready();
console.log(entity.foo.bar); // Outputs 'New value.'
Much like clearing the entity cache, you may need to refresh the entity's own data in PHP. Use the refresh
method, just like in JS, for this.
$entity = MyEntityClass::factory();
$entity->foo = 'Old value.';
$entity->save();
$instOfEnt = \Nymph\Nymph::getEntity(['class' => 'MyEntityClass'], ['&', 'guid' => $entity->guid]);
$instOfEnt->foo = 'New value.';
$instOfEnt->save();
echo $entity->foo; // Outputs 'Old value.'
$entity->refresh();
echo $entity->foo; // Outputs 'New value.'
To save an entity, use the save
method. Likewise, to delete the entity, use the delete
method. You can also call the saveEntity
, deleteEntity
, and deleteEntityById
methods of Nymph. The Entity
class uses these methods.
$entity = MyEntityClass::factory();
// Save the entity.
$entity->save();
// or
\Nymph\Nymph::saveEntity($entity);
// Delete the entity.
$entity->delete();
// or
\Nymph\Nymph::deleteEntity($entity);
// or
\Nymph\Nymph::deleteEntityById($entity->guid, 'MyEntityClass');
var entity = new MyEntityClass();
// Save the entity.
await entity.$save();
// or
await Nymph.saveEntity(entity);
// or
await Nymph.saveEntities(arrayOfEntities);
// Save only the data that has changed.
await entity.$patch();
// or
await Nymph.patchEntity(entity);
// or
await Nymph.patchEntities(arrayOfEntities);
// Delete the entity.
await entity.$delete();
// or
await Nymph.deleteEntity(entity);
// or
await Nymph.deleteEntities(arrayOfEntities);
Entities can't simply be checked using the == operator. It will almost always fail because of things like serialized data and sleeping references. Instead, you can use the following entity methods.
-
is
- Perform a less strict comparison of two entities. To return true, the entities must meet the following criteria.- They must be entities.
- They must have equal GUIDs, or both can have no GUID.
- If they have no GUIDs, their data must be equal.
-
equals
- Perform a more strict comparison of two entities. To return true, the entities must meet the following criteria.- They must be entities.
- They must have equal GUIDs, or both can have no GUID.
- They must be instances of the same class.
- Their data must be equal.
-
inArray
- Check whether the entity is in an array. Takes two arguments, the array and a boolean$strict
. If$strict
is false, the function usesis
to compare, and if it's true, the function usesequals
. -
arraySearch
- Search an array for the entity and return the corresponding key. Takes two arguments, the array and a boolean$strict
. If$strict
is false, the function usesis
to compare, and if it's true, the function usesequals
. This method may return 0, which evaluates to false, so you should useinArray
if you are only checking whether the entity is in the array.
$entity = MyEntityClass::factory(35); // Assuming this entity exists.
$entity2 = MyEntityClass::factory(35);
$entity->is($entity2); // True
$arr = [null, null, $entity];
$entity->arraySearch($arr); // 2
$entity->inArray($arr); // True
let entity = await new MyEntityClass(35).$readyPromise; // Assuming the entity with GUID 35 exists.
let entity2 = await new MyEntityClass(35).$readyPromise;
entity.$is(entity2); // True
const arr = [null, null, entity];
entity.$arraySearch(arr); // 2
entity.$inArray(arr); // True
There are three methods to sort entities.
-
hsort
- Sort an array of entities hierarchically by a specified property's value. -
psort
- Sort an array of entities by parent and a specified property's value. If they have the same parent, their own value is used. -
sort
- Sort an array of entities by a specified property's value.
$cats = \Nymph\Nymph::getEntities(['class' => FoobarCategory]);
$caseSensitive = false;
$reverse = false;
// Sort categories hierarchically by their name.
\Nymph\Nymph::hsort($cats, 'name', 'parent', $caseSensitive, $reverse);
// Sort categories by their parent's name.
\Nymph\Nymph::psort($cats, 'name', 'parent', $caseSensitive, $reverse);
// Sort categories by their name.
\Nymph\Nymph::sort($cats, 'name', $caseSensitive, $reverse);
let cats = await Nymph.getEntities({'class': FoobarCategory.class});
const caseSensitive = false;
const reverse = false;
// Sort categories hierarchically by their name.
Nymph.hsort(cats, 'name', 'parent', caseSensitive, reverse);
// Sort categories by their parent's name.
Nymph.psort(cats, 'name', 'parent', caseSensitive, reverse);
// Sort categories by their name.
Nymph.sort(cats, 'name', caseSensitive, reverse);
Client side Nymph entities can use the $serverCall
JavaScript method to call methods on a server side instance of the entity. This allows you to use a method that isn't yet, or won't be, implemented on the client side. $serverCall
expects three parameters: method, params, stateless
.
-
method
- the name of the method to call on the server side object. -
params
- an array of the parameters to pass to the method. In ES5, you can use thearguments
object for this, and it will be converted to a real array. -
stateless
- if set to true, will cause the method to not update the entity with the returned server side representation.
Normally, when you use this method, just before the promise is fulfilled, the entity's data will be replaced with that of the entity on the server side after the method was run. This will cause any awoken entities in the data of your entity to be replaced with sleeping entities, so you will have to run $readyAll
again. If you know that the server side method will not change any of the data on the entity, you can set stateless
to true.
You can also call static methods on the server with serverCallStatic
.
In order to be called from the client side, the method must be listed in the clientEnabledMethods
or clientEnabledStaticMethods
property in the PHP class. This guards against a user submitting tailored AJAX calls to perform potentially dangerous tasks on the server side. If the method is not listed, the AJAX request will fail with a 403 Forbidden status.
try {
const success = await todo.$serverCall('archive', []);
if (!success) {
alert("Couldn't archive " + todo.name);
}
} catch (errObj) {
alert('Error: ' + errObj.textStatus + "\nCouldn't archive " + todo.name);
}
// You can also create a shortcut function to do the same thing in your class prototype.
// You can see this actually done in the class definition in examples/todo/Todo.src.js
class Todo extends Entity {
// ...
static archiveAllDone(onlyOlderThanDay, ...args) {
return Todo.serverCallStatic('archiveAllDone', [onlyOlderThanDay, ...args]);
}
$archive(...args) {
return this.$serverCall('archive', args);
}
}
// You'd use them like this.
const success = await Todo.archiveAllDone(true);
let todo = new Todo();
const success = await todo.$archive();
Home | Setup Guide | API Docs | Full Code API Docs
© Copyright 2014-2019 SciActive.com