Uncaught TypeError: Cannot read property 'on' of undefined in raphael.js - raphael

Was using justgage node_module in the below code. On importing raphael.js for the same, getting the error Uncaught TypeError: Cannot read property 'on' of undefined. When I checked the method giving issue in the file, it was found that the method was already defined in the code.
Code giving issue is eve.on("raphael.remove", stopAnimation); on line 5216 in raphael.js but this method was already defined on line 185 as eve.on = function (name, f){}. Can anybody tell what is the problem ?
Code -
import React from 'react';
import 'justgage';
import 'raphael';
var timeOut=null,gauge=null;
export default React.createClass({
componentDidMount(){
this.update();
},
update(){
gauge=new JustGage({ id: "gauge", value: 67, min: 0, max: 100, title: "Visitors"});
document.getElementById("gage").innerHTML = gauge;
timeOut=setTimeout(this.update, 600);
},
getValue(){
var val = 25*Math.random();
if(val>100) { val=100-val;}
if(val<0) { val=val+10;}
return val;
},
componentWillUnmount: function() {
clearTimeout(timeOut);
},
render(){
return(<div className="coll-md-4">
<div id="gage"></div>
</div>);
}
});

Try to use https://www.npmjs.com/package/webpack-raphael package.
ps. if you haven't jQuery available globally, you can pass using imports-loader module:
import 'imports-loader?jQuery=jquery,this=>window!webpack-raphael/raphael';

Related

How to mock a computed property, when testing a Vue3 component with Jest

Situation
I am trying to test a simple Vue3 component with Jest. I want to evaluate whether a certain text is rendered. The decision is dependent on a boolean computed value (isNeverShowAgain), and I want to mock that computed value.
<template>
<div :class="{ modal: true, 'is-active': showDialog }">
....
<WelcomeText />
....
</div>
</template>
<script lang="ts">
....
export default defineComponent({
name: 'WelcomeMessage',
components: { WelcomeText },
data() {
return {
/** Whether to show the message this time*/
showDialog: false,
....
};
},
beforeMount() {
//Decide whether to actually show this dialog now, before mounting it, to avoid any flicker
this.showDialog = !this.isNeverShowAgain === true;
},
....
computed: {
/** Whether the welcome message has been permanently dismissed */
isNeverShowAgain(): boolean {
return this.$store.getters.neverShowWelcomeMessageAgain;
},
},
});
</script>
Like shown above, in the real world this computed value (isNeverShowAgain) is taken from a vuex store property, and this is where I am stuck. There are many posts that show how to mock the vuex store, but this seems overkill to me.
Question
How can I mock the isNeverShowAgain computed value, without mocking the complete vuex store?
Context
Here is my failing test:
/**
* #jest-environment jsdom
* #devdoc See https://github.com/vuejs/vue-test-utils-next/issues/194#issue-689186727 about the setup with "as any"
*/
import { mount } from '#vue/test-utils';
import WelcomeMessage from '#/components/WelcomeMessage.vue';
describe('WelcomeMessage.vue', () => {
it('should display the message', () => {
const wrapper = mount(WelcomeMessage, {
computed: {
isNeverShowAgain() {
return false;
},
},
} as any);
// wrapper.vm.setComputed({ isNeverShowAgain: false }); //Deprecated and does not work
// Assert the rendered text of the component
expect(wrapper.text()).toContain('Welcome');
});
});
Here is the error I get:
TypeError: Cannot read property 'getters' of undefined
69 | /** Whether the welcome message has been permanently dismissed */
70 | isNeverShowAgain(): boolean {
> 71 | return this.$store.getters.neverShowWelcomeMessageAgain;
| ^
72 | },
73 | },
74 | });
It's obvious that the problem is a not mocked vuex store, but again, how can I mock the computed value, that depends on the store in the first place?
Notes
Remember, this is Vue3 and the matching Jest2 test utils, so some previously available features are now deprecated like setComputed.
My dependencies
"devDependencies": {
.....
"#types/jest": "^27.0.2",
"#vue/test-utils": "^2.0.0-rc.16",
"#vue/vue3-jest": "^27.0.0-alpha.3",
"jest": "^27.3.1",
"jest-cli": "^27.3.1",
"ts-jest": "^27.0.7",
"ts-node": "^10.4.0",
"typescript": "~4.1.5",
},
You don't have to mock the computed but you have to mock the store like this:
const wrapper = mount(WelcomeMessage, {
$mocks: {
$store: {
getters: {
neverShowWelcomeMessageAgain: true
}
}
}
});

Apollo client & Absinthe - difficulty parsing errors

I'm working with the #apollo/client and #absinthe/socket-apollo-link NPM packages in my React app, but I'm having some trouble parsing query and mutation errors received by onError in my implementation of the useQuery and useMutation hooks.
For example, here is the way I've set up a query in my component:
useQuery(OperationLib.agendaQuery, {
fetchPolicy: "network-only",
onCompleted: ({ myData }) => {
setData(myData)
setLoading(false)
},
onError: (error) => {
console.log(error)
}
})
When that onError handler is called, the error object that is returned is logged as:
Error: request: [object Object]
at new ApolloError (app.js:36358)
at app.js:146876
at app.js:145790
at new Promise (<anonymous>)
at Object.error (app.js:145790)
at notifySubscription (app.js:145130)
at onNotify (app.js:145169)
at SubscriptionObserver.error (app.js:145230)
at app.js:58209
at Array.forEach (<anonymous>)
I can break this response into its parts "graphQLErrors", "networkError", "message", "extraInfo", but I'm finding it difficult to get any useful info there. In particular, I'd like to be able to get something out of the message - but in this case, error.message is the string,
request: [object Object]
typeof error.message logs string so yeah I can't really do anything with this.
Maybe I could find something useful under one of the other attributes? Nope, graphQLErrors is an empty array, networkError yields the same output as I got when I logged the initial error above, and extraInfo is undefined.
I dug into the source code and found the method createRequestError - when I added a debug log here to see what the message was, I good some good data - I could see the message that I would think would be available somewhere in the error response:
var createRequestError = function createRequestError(message) {
return new Error("request: ".concat(message));
}.bind(undefined);
What could be causing this issue? Is there something I need to configure in my Apollo/Absinthe initialization? I've set those up like so:
apollo-client.js
import { ApolloClient, InMemoryCache } from "#apollo/client"
import absintheSocketLink from "./absinthe-socket-apollo-link"
export default new ApolloClient({
link: absintheSocketLink,
cache: new InMemoryCache()
})
absinthe-socket-apollo-link.js
import * as AbsintheSocket from "#absinthe/socket"
import { createAbsintheSocketLink } from "#absinthe/socket-apollo-link"
import { Socket as PhoenixSocket } from "phoenix"
const protocol = window.location.protocol === "https:" ? "wss" : "ws";
const getToken = () => JSON.parse(window.localStorage.getItem("token"))
let token = getToken();
const params = {
get jwt() {
if (!token) {
token = getToken();
}
return token;
},
};
export default createAbsintheSocketLink(
AbsintheSocket.create(
new PhoenixSocket(`${protocol}://${WS_API_URL}/graphql`, {
reconnect: true,
params: params
})
)
);
Thanks much for any insight!

Ember JS: Highcharts.js into a component

Updated 03/17/2016 to better reflect current best practices for EmberJS v1.13.0 and up.
Problem
I am rendering Highcharts into a component and i almost have it working, but the binding of a property into the component is getting lost somewhere.
This is how I call the component:
//templates/index.hbs
{{pie-chart data=pieData}}
This is what the data property looks like (currently set in a controller):
//controllers/index.js
import Ember from 'ember';
export default Ember.Controller.extend({
init() {
this._super(...arguments);
this.pieData = [
['0 - 30', 2.5],
['31 - 60', 7.5],
['61 - 90', 12.5],
['91 - 120', 77.5]
];
}
});
And here is the component logic:
//components/pie-chart.js
import Ember from 'ember';
export default Ember.Component.extend({
classNames: ['chart'],
renderChart() {
return this.$().highcharts({
chart: {
height: 275
},
title: null,
plotOptions: {
pie: {
dataLabels: {
enabled: false
}
}
},
series: {
type: 'pie',
data: this.get('data')
},
colors: ['#777777', '#888888', '#999999', '#aaaaaa', '#bbbbbb', '#cccccc', '#dddddd', '#eeeeee'],
credits: {
enabled: true
}
});
},
didUpdateAttrs() {
let chart = this.$().highcharts();
let series = this.get('data');
chart.series[0].setData(series);
},
didInsertElement() {
this._super(...arguments);
this.renderChart();
},
willDestroyElement() {
this.$().highcharts().destroy();
}
});
i got the idea from this blog and i am trying to adapt it to make more charts.
the chart renders onto the screen, but it is blank... there are no errors to report... the only thing i can think is the data property is not being handled correctly in order to plot the graph?
I am not sure if this is my wrong use of Ember code, or wrong use of Highcharts code?
Solution
the series property inside the highchart was supposed to be an array of objects.. but I mistakenly defined just an object:
the fix:
series: [{
type: 'pie',
data: this.get('data')
}],
So, that is how you render a Highchart.js into a component :)

Ember-Model: Help Debug - TypeError: cannot read property 'map' of undefined

Summary
I am using Ember-Model and I need help debugging this error message.. it is actually two separate (but similar) error messages:
TypeError: Cannot read property 'map' of undefined
-and-
Uncaught Error: Assertion Failed: TypeError: Cannot read property 'map' of undefined
Details
In my app, there is a route called "view". It pulls a collection of accounts from an API.
I have the model and custom adapter defined almost correctly and I get a successful response from the server with a JSON payload. I do not know what to do next as there is an error in the console (see above).
Somewhere in the Ember-Model source code there is a property called map inside of the materializeData function, and do not know what it is trying to do... (I see a comment in that function // FIXME which is making me nervous)
Here is my code that got me to the problem:
View Model:
import ViewAdapter from '../../adapters/accounts/view';
var attr = Ember.attr, hasMany = Ember.hasMany, belongsTo = Ember.belongsTo;
var View = Ember.Model.extend({
debtor_id: attr(),
debtor_legacy_account_number: attr(),
debtor_full_name: attr(),
debtor_balance: attr()
});
View.adapter = ViewAdapter.create();
View.url = 'api/rest/debtor/list';
View.rootKey = 'data';
View.collectionKey = 'debtors';
View.primaryKey = 'debtor_id';
export default View;
View Adapter:
var ViewAdapter = Ember.RESTAdapter.extend({
buildURL: function(klass, id) {
var urlRoot = Ember.get(klass, 'url');
if (!urlRoot) { throw new Error('ViewAdapter requires a `url` property to be specified'); }
if (!Ember.isEmpty(id)) {
return urlRoot + "/" + id;
} else {
return urlRoot;
}
},
ajaxSettings: function(url, method) {
return {
url: url,
type: method,
headers: {
"Accept": "application/json; version=1.0.0"
},
dataType: "json"
};
}
});
export default ViewAdapter;
View Route:
import View from '../../models/accounts/view';
export default Ember.Route.extend({
model: function() {
return View.find({page_size: 10, page_number: 1});
}
});
Note: my use of the model hook here to pass parameters to the server is temporary, I am searching a better way to do server-side pagination in a separate case... but this at least works for now...
What am I missing?
Full Stack Trace
TypeError: Cannot read property 'map' of undefined
at Ember.RecordArray.Ember.ArrayProxy.extend.materializeData (http://local-03-02-xx.lariatcentral.net/assets/vendor.js:60646:24)
at Ember.RecordArray.Ember.ArrayProxy.extend.load (http://local-03-02-xx.lariatcentral.net/assets/vendor.js:60630:31)
at Ember.RESTAdapter.Ember.Adapter.extend.didFindQuery (http://local-03-02-xx.lariatcentral.net/assets/vendor.js:61925:15)
at http://local-03-02-xx.lariatcentral.net/assets/vendor.js:61916:12
at invokeCallback (http://local-03-02-xx.lariatcentral.net/assets/vendor.js:23709:19)
at publish (http://local-03-02-xx.lariatcentral.net/assets/vendor.js:23379:9)
at publishFulfillment (http://local-03-02-xx.lariatcentral.net/assets/vendor.js:23799:7)
at http://local-03-02-xx.lariatcentral.net/assets/vendor.js:29217:9
at DeferredActionQueues.invoke (http://local-03-02-xx.lariatcentral.net/assets/vendor.js:21747:18)
at Object.DeferredActionQueues.flush (http://local-03-02-xx.lariatcentral.net/assets/vendor.js:21797:15) vendor.js:17062
logToConsole vendor.js:17062
RSVP.onerrorDefault vendor.js:59834
__exports__.default.trigger vendor.js:22673
Promise._onerror vendor.js:23397
publishRejection vendor.js:23804
(anonymous function) vendor.js:29217
DeferredActionQueues.invoke vendor.js:21747
DeferredActionQueues.flush vendor.js:21797
Backburner.end vendor.js:21260
Backburner.run vendor.js:21315
apply vendor.js:21145
run vendor.js:19777
settings.success vendor.js:62014
fire vendor.js:3214
self.fireWith vendor.js:3326
done vendor.js:9370
callback
JSON Payload Sample
{
"status":"success",
"data":{
"debtors":[
{
"debtor_id":1048,
// ...
// ...
},
{
"debtor_id":1049,
// ...
// ...
},
{
"debtor_id":1050,
// ...
// ...
},
// ...more JSON...
],
"count":10,
"total":475,
"current_page":1,
"total_pages":48,
"page_size":10
}
}
I also found this github issue that looks exactly like my problem.
When you call View.find({page_size: 10, page_number: 1}); ember-model will send a request to the server, get the payload and call the didFindQuery hook. Since you're using the RESTAdapter the current implemantation is the following:
didFindQuery: function(klass, records, params, data) {
var collectionKey = Ember.get(klass, 'collectionKey'),
dataToLoad = collectionKey ? data[collectionKey] : data;
records.load(klass, dataToLoad);
},
The fourth param data is your payload. And because you setup the View.collectionKey to 'debtors' it will call records.load with data['debtors'] which returns undefined. That undefined value is passed to materializeData and you're receiving the TypeError: Cannot read property 'map' of undefined. What you need is data['data']['debtors'].
What you can do is:
Change your payload structure to:
{
"status":"success",
"debtors":[
{
"debtor_id":1048,
// ...
// ...
},
{
"debtor_id":1049,
// ...
// ...
},
{
"debtor_id":1050,
// ...
// ...
},
// ...more JSON...
],
"count":10,
"total":475,
"current_page":1,
"total_pages":48,
"page_size":10
}
}
Or override the didFindQuery and didFindAll to:
var ViewAdapter = Ember.RESTAdapter.extend({
// others methods ...
didFindQuery: function(klass, records, params, data) {
var collectionKey = Ember.get(klass, 'collectionKey'),
dataToLoad = collectionKey ? data['data'][collectionKey] : data;
records.load(klass, dataToLoad);
},
didFindAll: function(klass, records, data) {
var collectionKey = Ember.get(klass, 'collectionKey'),
dataToLoad = collectionKey ? data['data'][collectionKey] : data;
records.load(klass, dataToLoad);
}
})
I hope it helps

TypeError: Cannot read property 'Mixin' of undefined

I'm trying to use ember-validation. I added validation.mixin in my controller , but it cause error. This is my controller code:
var loanController = Ember.ObjectController.extend(Ember.Validations.Mixin);
loanController.reopen({
borrowingLimits:null,
industries:null,
actions:{
submitAction:function(){
var model=this.get('model');
if (model!=null) {
var controller = this;
$.ajax({
type :'post',
async:false,
url : '/api/v1/loanapplication/',
data: JSON.stringify(model),
contentType: "application/json; charset=utf-8"
}).done(function (data) {
controller.transitionToRoute('upload-documents',data);
});
}
}
},
validations: {
applicantFirstName: {
presence: true,
length: { minimum: 5 }
}
}
});
export default loanController;
how can I solve this problem?
update
I have added imports
app.import('vendor/ember-validations/packages/ember-validations/lib/core.js');
app.import('vendor/ember-validations/packages/ember-validations/lib/defaultMessages.js');
app.import('vendor/ember-validations/packages/ember-validations/lib/errors.js');
app.import('vendor/ember-validations/packages/ember-validations/lib/main.js');
app.import('vendor/ember-validations/packages/ember-validations/lib/mixin.js');
app.import('vendor/ember-validations/packages/ember-validations/lib/validatorNamespaces.js');
app.import('vendor/ember-validations/packages/ember-validations/lib/validators.js');
It seems like you might be incorrectly importing ember-validations but the root of the cause is that you're not importing the mixin into the controller file. The following will work.
In your Bower.json file:
{
"name": "app-name",
"dependencies": {
"ember-validations": "http://builds.dockyard.com.s3.amazonaws.com/ember-validations/ember-validations-latest.min.js",
}
}
Run bower install.
In your Brofile.js:
app.import('vendor/ember-validations/index.js');
In mixins/form-saving.js:
export default Em.Mixin.create(
Em.Validations.Mixin, {
// Your common form saving functions and properties
});
In controllers/loan.js:
import FormSaving from 'app-name/mixins/form-saving';
export default Em.ObjectController.extend(
FormSaving, {
// Methods and Properties here
});
Did you import the library?
Assuming you are using th ember-cli:
// in Brocfile.js after importing ember.js
app.import('vendor/path/to/ember-validations');