Controller required via $stateProvider not binding data to $scope - angularjs

I got a $stateProvider in my app with which i'm requiring a controller like below,
$stateProvider
.state('randomState', {
url: "/randomState",
templateUrl: "template.html",
controller: require('randomData')
});
the template.html is very simple that it has the below markup,
<simple-table data="tableData.data"></simple-table>
All i do in the controller is using the $http service, i hit an end point which provides me a JSON object and once the data is received, in the success callback i attach the $scope as $scope.tableData = data, but in the page i could see the <tr>'s getting populated but not the cells <td>, could not see any errors in the console, also when i log $scope.tableData i could see the proper object getting binded, any idea on why it is not binding the data's inside cell element.
I even tried encapsulating the $http service inside $timeout, but no luck. JSON response would look something like below,
{
"data": {
"columns": [
{"header": "Column header"},
{"header": "Column header"}
],
"data": [
[
"Row Header <br>(optional)",
"Lorem ipsum dolor sit amet, consectetur adipiscing elit.",
"$7.50B",
"427,576,608",
"$7.50B"
],[
"Row Header",
"Lorem ipsum dolor sit amet, consectetur adipiscing elit.",
"45.06",
"+24.54%",
"45.06"
]
]
}
}

Related

react-jsonschema-forms validator error - Cannot read properties of undefined (reading 'replace')

I'm trying to build dynamic forms using rjsf and having some issues with the validator.
The error message is applicable to any validation type attempt i.e. if a field is required or minLenght check.
If I disable noHtml5Validate={false} then I get a pop up telling me to populate required field. My goal is to display all errors and highlight relevant inputs in red.
This corresponds to this line in the code:
var property = instancePath.replace(/\//g, ".");
My schema is:
const testSchema = {
"type": "object",
"required": [
"account",
],
"properties": {
"reference": {
"type": "string",
"description": "Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua",
"nullable": true,
},
"account": {
"type": "integer",
"format": "int64",
"pattern":"^(0|[1-9][0-9]*)$",
}
},
"additionalProperties": false
};
import Form from "#rjsf/bootstrap-4";
import validator from "#rjsf/validator-ajv8";
return <>
{ schema && <Form
schema={testSchema}
uiSchema={uiSchema}
validator={validator}
onSubmit={onSubmit}
noHtml5Validate={true}
formData={formData}
onChange={(e)=> onChangeHandler(e.formData)}
/>}</>;
What is more confusing is that when I set up a new test app using npx create app and use the same settings it works just fine so I'm really unsure to resolve this issue. I've already spent 3 days searching for a solution

Angular Typescript - Property 'files' does not exist on type 'string | { ... }'

I'm starting on Angular and Typescript and I'm currently stumbling on a problem, so I'm looking for some guidance. Indeed, I would like to create something like this:
Structure Mockup
But I'm getting the follow error in my IDE saying:
Property 'files' does not exist on type 'string | { id: string; name: string; img: string; videos: number[]; files: number[]; }'
However, my console.log are well displaying so I don’t understand
Here is a summary of my code:
public meal = [
{
id : "0",
title:"Ingredients",
ingredients: [
{id:"0", name:"Lorem ipsum", img:"assets/loremipsum.png", videos:["0"], files:["0","1"]},
{id:"1", name:"Lorem ipsum", img:"assets/loremipsum.png", videos:["1"], files:["0"]},
{id:"2", name:"Lorem ipsum", img:"assets/loremipsum.png", videos:["0", "2"], files:["1"]},
{id:"3", name:"Lorem ipsum", img:"assets/loremipsum.png", videos:["1", "2"], files:["0"]}
],
videos:[
{id:"0", url:"loremipsum"},
{id:"1", url:"loremipsum"},
{id:"2", url:"loremipsum"}
],
files:[
{id:"0", title:"Lorem ipsum", link:"assets/loremipsum.pdf"},
{id:"1", title:"Lorem ipsum", link:"assets/loremipsum.pdf"}
],
questions:[
{id:"0", question:"Lorem ipsum ?", answer:"Lorem ipsum dolor sit amet, consectetur adipiscing elit"},
{id:"1", question:"Lorem ipsum ?", answer:"Lorem ipsum dolor sit amet, consectetur adipiscing elit"},
{id:"2", question:"Lorem ipsum ?", answer:"Lorem ipsum dolor sit amet, consectetur adipiscing elit"}
]
},
{
id : "1",
title:"Restaurants",
ingredients:[],
videos:[
{id:"0", url:"loremipsum"}
],
files:[
{id:"0", title:"Lorem ipsum", link:"assets/loremipsum.pdf"},
{id:"1", title:"Lorem ipsum", link:"assets/loremipsum.pdf"}
],
questions:[
{id:"0", question:"Lorem ipsum ?", answer:"Lorem ipsum dolor sit amet, consectetur adipiscing elit"},
{id:"1", question:"Lorem ipsum ?", answer:"Lorem ipsum dolor sit amet, consectetur adipiscing elit"}
]
},
{
id : "2",
title:"Equipment",
ingredients:[],
videos:[],
files:[
{id:"0", title:"Lorem ipsum", link:"assets/loremipsum.pdf"},
{id:"1", title:"Lorem ipsum", link:"assets/loremipsum.pdf"}
],
questions:[
{id:"0", question:"Lorem ipsum ?", answer:"Lorem ipsum dolor sit amet, consectetur adipiscing elit"},
{id:"1", question:"Lorem ipsum ?", answer:"Lorem ipsum dolor sit amet, consectetur adipiscing elit"}
]
}
]
ngOnInit(): void {
this.getRouteParams();
}
getRouteParams() {
this.routeSub = this.activatedRoute.queryParams.subscribe(params => {
if(params['id']){
this.mealId = params['id'];
}
else{
this.mealId = "0";
}
this.IngredientFiles();
});
this.routeSubFragment = this.activatedRoute.fragment.subscribe(fragments => {
if(fragments){
this.ingredientId = fragments;
}
else{
this.ingredientId = "0";
}
this.IngredientFiles();
});
}
IngredientFiles() {
let filesDisplayed = [];
if(this.meal[this.mealId].ingredients.length > 0){
for(let mealFile of this.meal[this.mealId].files){
console.log("mealFile: "+mealFile.id) // WORKS
if(this.meal[this.mealId].ingredients[this.ingredientId].files.length > 0){
for(let ingredientFile of this.meal[this.mealId].ingredients[this.ingredientId].files){
if (ingredientFile == mealFile.id){
console.log("ingredientFile: "+ingredientFile) // WORKS
filesDisplayed.push(ingredientFile)
}
}
}
}
}
}
Thank you in advance for helping
The line "Property 'files' does not exist on type 'string | { id: string; name: string; img: string; videos: number[]; files: number[]; }'" means that TypeScript is trying to guess the typing of meal based on its value. The error comes from it not guessing quite right. And console.log shows a value, because the value is actually there.
Not declaring type for complex structures like this is generally a bad idea (think about yourself a few weeks for now, trying to recall "what is supposed to go into a meal?"). You can use sth like
type Ingredient = {
id: string;
name: string;
img: string;
videos: string[];
files: string;
}
type Video = // definition here
// the rest of the definition
type Meal = {
id: string;
name: string;
ingredients: Ingredient[];
videos: Video[];
files: FileEntry[]; // `File` is reserved
questions: Question[];
}
//...
meal: Meal[] = { // actual value here

Ext JS 6 - DataView - ItemClick not attached

I've been unable to add an itemclick listener to what I thought was a very simple example. The view is shown correctly with the repeated HTML. Can anyone help with where I've gone wrong?
Ext.define('App.view.Stuff', {
extend: 'Ext.DataView',
alias: 'view.stuff',
store: [{
"title": "Dataset 1",
"desc": "Lorem ipsum dolor sit amet."
}, {
"title": "Dataset 2",
"desc": "Lorem ipsum dolor sit amet."
}],
listeners: {
itemclick: function () {
console.log('itemclick');
},
},
itemTpl:
'<div><strong>{title}</strong></div>' +
'<div>{desc}</div>'
});
Since v6.5.0 the event is called childsingletap.
childsingletap ( this, location, eOpts )
Fires when a child is single tapped.
Available since: 6.5.0
Parameters
this : Ext.dataview.DataView
This dataview.
location : Ext.dataview.Location
The location for the event.
eOpts : Object
The options object passed to Ext.util.Observable.addListener.
Here's the working code:
Ext.define('App.view.Stuff', {
extend: 'Ext.DataView',
alias: 'view.stuff',
store: [{
"title": "Dataset 1",
"desc": "Lorem ipsum dolor sit amet."
}, {
"title": "Dataset 2",
"desc": "Lorem ipsum dolor sit amet."
}],
listeners: {
childsingletap: function () {
console.log('childsingletap');
},
},
itemTpl:
'<div><strong>{title}</strong></div>' +
'<div>{desc}</div>'
});

Unknown provider: $xProvider <- $xService

I'm having an issue with Karma and Jasmine while using AngularJS. What I'm trying to do is test a controller that will make some posts available to the view from a service. Here's my controller:
app.controller('PostController', function($scope, $postService) {
$scope.posts = $postService.getPosts();
});
And here is my test:
describe('PostController', function(){
var posts, $postService;
beforeEach(module('cms'));
beforeEach(function() {
posts = [
{
title: 'Article title',
tags: [
{ name: 'Tag #1', link: 'posts/tagged/tag-1' },
{ name: 'Tag #2', link: 'posts/tagged/tag-2' },
{ name: 'Tag #3', link: 'posts/tagged/tag-3' }
],
body: 'Lorem ipsum dolor sit amet, consectetur adipiscing elit. Duis efficitur nisi nec neque molestie ultricies. ' +
'Mauris facilisis libero lorem. Praesent pulvinar dictum justo, at tincidunt magna convallis at. Integer' +
'laoreet justo vel faucibus placerat. Sed quis elit vel ante dictum dictum. Mauris ut ullamcorper tortor.' +
'Phasellus finibus ex justo, eget rutrum felis lobortis tincidunt. Curabitur hendrerit elit enim, a fermentum' +
'odio egestas mollis.',
author: { name: 'Dan', link: 'users/Dan-1' },
postDate: '0 seconds ago'
}
]
postService = {
getPosts: function() { return posts; }
};
})
it('should create "posts" model with posts from PostService', inject(function($controller) {
var scope = {},
ctrl = $controller('PostController', {$scope: scope, $postService: postService});
expect(scope.posts).toEqual(posts);
}));
});
The test works in this state, however I will be unable to run the controller at runtime because there is no explicit dependency;
Error: [$injector:unpr] Unknown provider: $postServiceProvider <- $postService
However, if I wrap the controller in something like this:
app.controller('PostController', ['$postService', inject(function($scope, $postService) {
$scope.posts = $postService.getPosts();
}
Then the controller will work at runtime, however in testing, $postService will always be undefined from inside of the controller.
Has anyone come across this issue, and if so, what am I missing here?
Try this:
you are missing $scope
app.controller('PostController', ['$scope', '$postService', function($scope, $postService) {
$scope.posts = $postService.getPosts();
}]);

Voting widget to have a minimum of zero (no negatives)

I have a voting widget where visitors to a site can vote up or down on their favorite game. However, visitors are able to down vote to the negatives too!
For example, if the current voteCount on my game object on the scope is set to 0, a user can come along, press the down arrow and change it to -1. How can I stop this from happening?
I can do this manually by doing a check before the voting happens, but is there no angular filter to do this?
Also, what is the quickest way to allow a user a single vote instead of endless votes? Would cookies be the quickest way? or HTML5's LocalStorage?
CTRL CODE
myApp.controller('VotingCtrl', function($scope){
$scope.games = [
{
name: 'Watch Dogs',
description: 'Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nam ut felis dapibus, bibendum dui eu.',
imgUrl: 'img/watchdogs.jpg',
voteCount: 0
},
{
name: 'Thief',
description: 'Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nam ut felis dapibus, bibendum dui eu.',
imgUrl: 'img/thief.jpg',
voteCount: 0
},
{
name: 'Fifa 2014',
description: 'Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nam ut felis dapibus, bibendum dui eu.',
imgUrl: 'img/fifa2014.jpg',
voteCount: 0
}
]
$scope.voteUp = function(game) {
game.voteCount += 1;
};
$scope.voteDown = function(game) {
game.voteCount -= 1;
};
});
One way is to change your voteDown method to not decrement if voteCount = 0.
The other way (which I would prefer) is to disable downVote button if the voteCount has reached 0, using ng-disabled. This will make it clear to the user that he/she cannot downvote anymore.
Edit: Pseudo Code for using ng-disabled.
In your view, you can do something like, assuming you are disabling a span.
<span ng-disabled="isDownVoteDisabled(game)"></span>
In your controller, you can define
$scope.isDownVoteDisabled = function(game) {
return game.voteCount <= 0;
}
Abhi.

Resources