I've added a custom method called customMethod to a model, like so:
class Prize extends Model {
customMethod(){
return 'test'
}
}
When I use find to get a prize by primary key I can call this method no problem
const prize = await Prize.find(1);
return prize.customMethod();
//returns 'test'
but when if I get a prize any other way, through a relationship or by querying by a field, I can't access this method.
const countrysPrizes = await country.prizes().fetch();
for (const key in countrysPrizes) {
if (countrysPrizes.hasOwnProperty(key)) {
const prize = countrysPrizes[key];
return prize.customMethod();
//returns 500 - prize.customMethod is not a function
}
}
How can I access this method while iterating through multiple of the object?
You need to use <fetched_object>.rows because of VanillaSerializer
Example code :
const user = await User.find(1);
const posts = await user.posts().fetch();
posts.rows.forEach(post=> { // use .rows
console.info(post.customMethod()); // Your custom method
});
I've had trouble using the basic foreach loop. So I used .foreach()
An output example with fetch() :
Related
We have an issue with my team where a RESTDataSource class has many methods and it makes the file 1500 lines long.
This class can be split into multiple themes, for instance a Facebook datasource has some methods about the user, some methods about the article...
Has anyone a method to split this class so that it becomes less messy?
For info this is the class I am talking about (but 1500 lines long) :
const { RESTDataSource } = require('apollo-datasource-rest');
class MoviesAPI extends RESTDataSource {
constructor() {
// Always call super()
super();
// Sets the base URL for the REST API
this.baseURL = 'https://movies-api.example.com/';
}
async getMovie(id) {
// Send a GET request to the specified endpoint
return this.get(`movies/${encodeURIComponent(id)}`);
}
async getMostViewedMovies(limit = 10) {
const data = await this.get('movies', {
// Query parameters
per_page: limit,
order_by: 'most_viewed',
});
return data.results;
}
}
I am trying to group users by date that is in the relationship accesses and page this result.
Model User
public function acessos()
{
return $this->hasMany(Acessos::class,'id_usuario');
}
Model Acessos
public function user()
{
return $this->belongsToMany(User::class,'id_usuario');
}
Livewire component
$data = User::query()
->search($this->search)
->with('acessos')
->has('acessos')
->paginate($this->perPage);
return view('livewire.relatorios.acessos.acessos-component',[
'data' => $data
]);
Remove the user() method from Acessos Model and change the hasMany() method to belongsToMany in User model's acessos method. This Will solve your problem.
Remove this:
public function user()
{
return $this->belongsToMany(User::class,'id_usuario');
}
And change this:
public function acessos()
{
return $this->belongsToMany(Acessos::class,'id_usuario');
}
I am trying to write a seed file for users and profiles with a one to one relationship and currently getting an "error: relation 'user_profiles' does not exist". From digging around, it seems like Adonis will assume this as a pivot table in the case of a many to many relationship. What I (think or intend to) have is a one to one relationship between users and profiles. Thanks in advance! Newbie to SQL and Adonis. As a side note, the user persists to the db, but there is no corresponding profile.
// My User Schema
class UserSchema extends Schema {
up () {
this.create('users', (table) => {
table.increments('id')
table.string('username', 80).notNullable().unique()
table.string('email', 254).notNullable().unique()
table.string('password', 60).notNullable()
// table.integer('profile_id').unsigned().references('id').inTable('userprofiles')
table.timestamps()
})
}
down () {
this.drop('users')
}
}
// My Profile Schema
class UserprofileSchema extends Schema {
up () {
this.create('userprofiles', (table) => {
table.increments()
table.string('first_name')
table.string('last_name')
// table.integer('user_id')
// .unsigned().references('id').inTable('users')
table.integer('user_id')
.unsigned()
.index('user_id')
table.foreign('user_id')
.references('users.id')
table.timestamps()
})
}
down () {
this.drop('userprofiles')
}
}
My User model includes the following relationship definition:
profile () {
return this.hasOne('App/Models/UserProfile')
}
// Seed script
class UserSeeder {
async run () {
try {
const user = await Factory.model('App/Models/User').create()
const userProfile = await Factory.model('App/Models/UserProfile').make()
userProfile.user_id = user.id
await user.profile().save(userProfile)
} catch (e) {
console.log('Error From Seeder: ', e);
}
}
}
Error code '42P01' and can post whole body if needed. Thanks!
On your Model userProfile, set table name as follows.
class User extends Model {
static get table () {
return 'userprofiles'
}
}
When I select an item I want to check some fields before it will be displayed in the Field Editor and then change values on other fields.
So I need to subscribe to an event, but such event doesn't exist out of the box as I can see. Is there a way to hook to item selection action or I need to create a custom event, if so - where do I need to raise it?
Sounds like you need to create a custom validator - this blog post describes the process:
https://www.habaneroconsulting.com/stories/insights/2016/creating-a-custom-field-validator-in-sitecore
In summary:
Create a new field rule (Field validators are located in /sitecore/system/Settings/Validation Rules/Field Rules/) linking to your assembly. The blog post above gives the following example of a field validator
[Serializable]
namespace MySitecore.Project.Validators
{
// This validator ensures that the description attribute of a link is specified
public class LinkTextValidator : StandardValidator
{
public override string Name
{
get { return "Link text validator"; }
}
public LinkTextValidator() {}
public LinkTextValidator(SerializationInfo info, StreamingContext context) : base(info, context) { }
protected override ValidatorResult Evaluate()
{
Field field = this.GetField();
if (field == null)
return ValidatorResult.Valid;
string str1 = this.ControlValidationValue;
if (string.IsNullOrEmpty(str1) || string.Compare(str1, "<link>", StringComparison.InvariantCulture) == 0)
return ValidatorResult.Valid;
XmlValue xmlValue = new XmlValue(str1, "link");
string attribute = xmlValue.GetAttribute("text");
if (!string.IsNullOrEmpty(xmlValue.GetAttribute("text")))
return ValidatorResult.Valid;
this.Text = this.GetText("Description is missing in the link field \"{0}\".", field.DisplayName);
// return the failed result value defined in the parameters for this validator; if no Result parameter
// is defined, the default value FatalError will be used
return this.GetFailedResult(ValidatorResult.CriticalError);
}
protected override ValidatorResult GetMaxValidatorResult()
{
return this.GetFailedResult(ValidatorResult.Error);
}
}
}
Credit to: MICHAEL ARMSTRONG
I have the following controller method
public ActionResult Create(Category category)
{
//default values
if (string.IsNullOrEmpty(category.GeoAreaLevelIdentifier))
{
category.GeoAreaLevelIdentifier = "OutputArea";
}
category.CreatorIdentifier = EsdContext.User.UniqueIdentifier.ToString();
category.Created = DateTime.Now;
//validation
RevalidateModel(category);
new CategoryBroker().Create(category);
return JsonNow(category);
}
which fills some default values to the model and THEN validates it. This is because the client code is allowed to submit a model without some of the required fields. The missing fields are filled by the controller (see above).
RevalidateModel method calls TryValidateModel:
protected void RevalidateModel(object model)
{
ModelState.Clear();
TryValidateModel(model); //called explicitly since model has been updated
if (!ModelState.IsValid)
{
//error message
}
}
But when I call Create method from a unit test, it fails because TryValidateModel expects controllerContext:
Value cannot be null.Parameter name: controllerContext
What is the best way to solve this problem?
Should I create the controllerContext eg by MvcContrib TestHelper?
In this case
using Moq;
.........
readonly MockRepository _mockRepository = new MockRepository(MockBehavior.Default);
.........
controller.ControllerContext = _mockRepository.Create<ControllerContext>().Object;
works good enough.
Best.