Sequelize: add default scope with a function - javascript

I was working on adding default scopes with function under the Sequelize ORM. I followed the tutorials here http://docs.sequelizejs.com/manual/scopes.html while for Scope takes arguments, we need to pass on object like this
Project.scope('random', { method: ['accessLevel', 19]}).findAll();
So inside my video model code, I add a scope called 'defaultScope'
Video.addScope(
'defaultScope',
(userId) => {
*********** scope description here*********
})
And this is how I use my model:
const videos = await models.video.scope({
method: ['defaultScope', 'I hardcode userId here']
}).findAll();
console.log(videos);`
But I always got an error (node:43214) UnhandledPromiseRejectionWarning: SequelizeScopeError: Invalid scope null called.
If I use another scope name instead of 'defaultScope', my code works and I successfully got the objects back. However since it's a broad level scope I want to make it default. I just feel so confused why the normal scope works but default one not. Can somebody with relevant experience help me figure this out? Thanks!

Related

Why use AngularJs .constant() if I can declare JS const?

I'm working on an AngularJS project where there is a .constant() provider to declare some basic information used across the whole project. For example, a definition of cookie name. Ex.:
.constant('appConst', {
cookie: 'CookieName',
...
});
But the same thing can be done by declaring a const, ex.:
const appConst = {
cookie: 'CookieName',
...
}
So, what is the advatage of using the .constant provider instead of just declaring a const? I know one of the reasons is because we don't expect the value to change. But isn't this the same objective of a const?
The new const keyword only makes it so you cannot reassign the variable, it doesn't make any object you initially assign to it immutable. So in your example with:
const appConst = {
cookie: 'CookieName',
...
}
You would still be able to change the value of cookie. You just wouldn't be allowed to do something like this:
appConst = { // My new object };
The values in the angular .constant() can also still be changed, so they're not constant in the common use of the word "constant". At least not when you use it like this:
.constant('appConst', {
cookie: 'CookieName',
...
});
So if you for instance do like this and change the value within a controller
app.controller('myController', function(appConst){
appConst.cookie = 'NewCookieName';
})
the change would be reflected anywhere you inject appConst after this controller was constructed.
You can't "reassign" appConst in this case though, that action would just be ignored, so it is constant in that sense.
1- const is new in ES6, so you may need to transpiler your code for supporting old browsers.
2- const is block-scoped, so within a scenario, you define a constant in A.js, will be not able to use it at B.js unless you're using a module bundler, so we went back to the topic 1-.
The main purpose of AngularJS having this native is to able you to share it between controllers, services, and directives, using its dependency injection system.

Angular Component: how to specified value for output binding function defined in parent?

I wanted to use Angular 1.5's component to get benefit from its one-way binding: <hero-detail hero="ctrl.hero" save="ctrl.save(hero)"></hero-detail>. But, as Todd Motto points on his blog: Todd Motto's blog: One-way data-binding in Angular 1.5, it works properly only for primitives. So I had to bind primitives:
<hero-detail
name="ctrl.hero.name"
id="ctrl.hero.id"
save="ctrl.save(ctrl.hero)"
></hero-detail>
And next in component, on $onInit hook, make hero object from primitives:
HeroDetailController.prototype.$onInit = function(){
this.hero = {
name: this.name,
id: this.id
}
console.log('OnInit called');
}
And call specified function when user clicks save. Weird part is, that if user changes hero's name inside component and clicks save, when function bound from parent is called, it does not have changes from hero-detail component. I made a plunker which shows my problem: Plunk which shows problem with children/parent output binding in Angular 1.5 - if you open Developer Console, click "Set name..." and then click save, you will see console.logs which will show you that from hero-detail it is Spawn2, but in parent context (where should be logic, like talking to $http service), it has still old value Spawn. Am I missing something?
Code from Angular docs looks pretty like my code:
<button ng-click="$ctrl.onDelete({hero: $ctrl.hero})">Delete</button>
I have no clue what's going on. Thank you in advance for helping me to deal with this problem.
P.S. I had some problem with Plunk versions, now everything is OK - in Developer Console in your browser you can see problems with updates
To avoid confusion about the scope of variables (parent or child), prefix injected variables with $.
/* WAS
<hero-detail
name="ctrl.hero.name"
id="ctrl.hero.id"
save="ctrl.save(ctrl.hero)"
></hero-detail>
*/
//SHOULD BE
<hero-detail
name="ctrl.hero.name"
id="ctrl.hero.id"
save="ctrl.save($hero)"
></hero-detail>
Then in your code:
HeroDetailController.prototype.saveHero = function(hero) {
console.log('Hero name from child: ' + hero.name);
this.save({
$hero: hero
});
};
This way you can tell which variables of the expression are from the parent scope and which variables are from the directives scope.

Angular Updating scope variables after returning from a promise

I am using the q service in one of my controllers to make sure my requests finish before binding the responses in the then clause. Now here is the tricky part. There is a directive on the page who's template updates a scope variable. This scope variable is used to switch between different parts of the response json, A selector if you will. I need to updated a variable set in the then clause after the page is loaded. It is set by the id added in a directive.
I can't seem to figure out an efficient way to go about updating them.
$scope.selector = {}; //property added from a child scope
$q.all({
//some factory calls and assignment to properties
}).then(function(responses){
//scope variable assignments off of the responses object.
//some assignment that uses the selector. a[selector.id] ex.
}, function(err){
$log.error(err);
}).finally(function(){
//some setting of load params
});
//Then I need to update those variables set in the then based on whether or not the selector id was changed in the directive template.
Any help would be greatly appreciated.
Taking a guess here as the question isn't clear but from the looks of it, you should just save the entire set of responses on the scope and then pull out the data you need. I don't see why you are trying to update the entire response everytime you want to pull one aspect out.
$scope.selector = {}; //property added from a child scope
$scope.responses = {};
$q.all({
//some factory calls and assignment to properties
}).then(function(responses){
//scope variable assignments off of the responses object.
//some assignment that uses the selector. a[selector.id] ex.
$scope.responses = responses;
}, function(err){
$log.error(err);
}).finally(function(){
//some setting of load params
});
// Use something like $watch here and have it call a function
Watchers in AngularJS might be helpful as well.

Why do I need to call a dynamic route ":_id" and not whatever I want?

Here's a rather standard way to set a route in Iron Router:
Router.route('/posts/:_id', {
name: 'postPage',
data: function() { return Posts.findOne({_id: this.params._id}) }
});
Experimenting around a little, beginner as I am, I tried:
Router.route('/posts/:whatever', {
name: 'postPage',
data: function() { return Posts.findOne({_id: this.params.whatever}) }
});
This works well, up to a point. True, whatever will scoop up whatever is after /posts/ as its value, and the data context will indeed be the same as before... but linking to specific posts now won't work!
So,
{{title}}
simply won't work doing it "my" way (linking to nothing at all).
I can't fully wrap my head around this, and I'm too much of a novice to grasp the source code for Iron Router, so my hope is that someone here can explain it in a manner that even a beginner like me can comprehend.
Preferably like something like this:
First {{pathFor 'postPage'}} looks inside the routes to find the one named postPage.
It sees that this route corresponds to /posts/ followed by something else.
Looking inside the data context it finds that only one post is returned, namely the one with the same _id as whatever comes after /posts/.
It understands that it should link to this post, cleverly setting the url to /posts/_id.
This is wrong, most likely, and it doesn't explain why it would work when whatever is turned into _id. But it would help me immensely to see it parsed in a similar fashion.
Edit: Cleaned up my question so it is easier to grasp.
There's a simple set of circumstances that together lead to confusion:
The Posts.findOne issue is explained by the fact that the first argument can be either a selector or a document _id. So it's not really a shortcut but rather a documented feature.
As you found, putting :something in the iron:router URL causes that value to be reported as this.params.something inside the route function. This also registers something as an parameter to that route, which brings us to how pathFor works.
The pathFor helper takes two inputs: first the name of the route (in this case 'postPage') and second an object of parameters, which can come either from the second argument as in {{pathFor 'postPage' params}} or from the data context like so: {{#with params}}{{pathFor 'postPage'}}{{/with}}.
Now, here's why passing in a document from the database works if you call the parameter _id but not if you call it whatever: the post object that you retrieved from the database _has an _id field, but it doesn't have a whatever field. So when you pass it into pathFor, it only passes along the correct _id if the parameter to the route also happens to be called _id.
Let me know if that makes sense, I agree that this is somewhat confusing and that this "shortcut" hides what exactly pathFor and params actually do.

Passing object available in the template into the {{render}} helper doesn't seem to work

I have an object defined globally as App.configObj which contains a property data. Inside a view's template I can use {{App.configObj.data}} to display the value and it works fine.
Inside that same template, I use {{render "viewC" model config=App.configObj}} to render a similar view, but the config property on that view remains null on didInsertElement. Other arguments set to primitive values are correctly set at that point.
Since App.configObj is definitely available in that context, shouldn't I be able to pass it into that view?
Here is the jsbin that illustrates the situation: http://emberjs.jsbin.com/misiyaki/12/edit
If you comment out the render call for ViewC, you can see that {{App.configObj.data}} renders just fine in the template.
My goal is to use an object encapsulating several properties to configure the view, so I need to be able to pass that object in. I spent a lot of time searching for similar content online but didn't find anyone trying this.
What am I missing?
Thanks!
I understand your struggle here with not being able to pass in a property in your render code... but in this case it doesn't seem that that is truly necessary.
Here is a fiddle with some changes to show you another way, that is essentially the same thing if i understood your intentions correctly. http://emberjs.jsbin.com/misiyaki/15/edit
The new code for your view:
App.ViewCView = Em.View.extend({
name: 'testName',
config: function () {
return App.configObj;
}.property(),
data: function () {
return this.get('config.data')
}.property('config'),
templateName: 'view-c'
});
Hope this helps!

Categories

Resources