Node JS : Route.get() requires a callback function but got a [object Undefined] While using ES6 Modules - javascript

Route File
scoreboardroute.js
import { scoreRouteController } from '../controllers/scoreboardcontroller';
const SCOREROUTE = app => {
app.route('/getAllScores').get(scoreRouteController.getAllScores);
};
export { SCOREROUTE };
Controller File
scoreboardcontroller.js
import { scoreBoardModel } from '../model/scoreboardmodel';
class scoreRouteController {
getAllScores = (req, res) => {
scoreBoardModel.getAllScoresList((err, response) => {
if (err) {
res.send(err);
}
res.send(response);
});
};
}
export { scoreRouteController };
Model File:
scoreboardmodel.js
import { db } from './db';
class scoreBoardModel {
getAllScoresList = callback => {
db.query('Select * from users', (err,response) => {
callback(err, response);
});
}
};
export { scoreBoardModel };
I was trying to use ES6 features like class and arrow functions inside my application. While I'm trying to execute this code it hit the following error. I don't know what went wrong. And I'm really new for node JS server.
So, Can anyone please help me to get rid of this error.
Error:
node_modules/express/lib/router/route.js:202
throw new Error(msg);
^
Error: Route.get() requires a callback function but got a [object Undefined]
at Route.(anonymous function) [as get] (/node_modules/express/lib/router/route.js:202:15)
at SCOREROUTE (/app/routes/scoreboardroute.js:4:32)
at Object. (/server.js:26:1)
at Module._compile (internal/modules/cjs/loader.js:689:30)

I'm finding the answer.
While importing the class I'm using like Object import. So, changed it like
import scoreRouteController from '../controllers/scoreboardcontroller';
And I'm not going to use so many instances for my application. So, I assign static keyword for my every function inside my class.
static getAllScores = (req, res) => {.....
While exporting I was not exporting an Obj. I changed into default class export.
export default scoreRouteController;
And finally, it works.

Related

How to use Peer.js in Next.js with TypeScript?

Next.js runs on server side also, so Peer.js raise error when using Next.js. Here one says: https://stackoverflow.com/a/66292100/239219
this is probably because peer js is performing some side effect during import.
He propose this:
useEffect(() => {
import('peerjs').then(({ default: Peer }) => {
// Do your stuff here
});
}, [])
But I need DataConnection as using Typescript, and also asign it to a useState. would you show an example how?
This is what I put togeter, but TypesScript raise errors:
useEffect(() => {
import('peerjs').then(({ default: Peer, DataConnection }) => {
const peer = new Peer(localStorage.token)
peer.on('connection', (conn: DataConnection) => {
console.log('Connected to peer:', conn)
conn.on('data', (data) => {
console.log('Received data:', data)
})
})
return () => {
peer.destroy()
}
})
}, [])
like: 'DataConnection' refers to a value, but is being used as a type here. Did you mean 'typeof DataConnection'?
You can use a type-only import (introduced in version 3.8) at the top of the file:
import type { DataConnection } from "peerjs";
This import will be erased in the output, so rest assured that this will not import it "early".
Or if that doesn't fancy you, you can also "inline" the import:
peer.on('connection', (conn: import("peerjs").DataConnection) => {
Looks weird, but when import(...) is used as a type, it resolves to the namespace that importing the module would give you.

How is this anonymous function being called

I came across this code:
export default async function (req, res) {
...
}
This appears to be an anonymous function and it does get called when the app is run, but but I don't know how it can get called.
NOTE: This is part of a Nodejs app.
The entire code that it is part of is located in a single file:
import { Configuration, OpenAIApi } from "openai";
const configuration = new Configuration({
apiKey: process.env.OPENAI_API_KEY,
});
const openai = new OpenAIApi(configuration);
export default async function (req, res) {
if (!configuration.apiKey) {
res.status(500).json({
error: {
message: "OpenAI API key not configured, please follow instructions in README.md",
}
});
return;
}
const animal = req.body.animal || '';
if (animal.trim().length === 0) {
res.status(400).json({
error: {
message: "Please enter a valid animal",
}
});
return;
}
try {
const completion = await openai.createCompletion({
model: "text-davinci-003",
prompt: generatePrompt(animal),
temperature: 0.6,
});
res.status(200).json({ result: completion.data.choices[0].text });
} catch(error) {
// Consider adjusting the error handling logic for your use case
if (error.response) {
console.error(error.response.status, error.response.data);
res.status(error.response.status).json(error.response.data);
} else {
console.error(`Error with OpenAI API request: ${error.message}`);
res.status(500).json({
error: {
message: 'An error occurred during your request.',
}
});
}
}
}
function generatePrompt(animal) {
const capitalizedAnimal =
animal[0].toUpperCase() + animal.slice(1).toLowerCase();
return `Suggest three names for an animal that is a superhero.
Animal: Cat
Names: Captain Sharpclaw, Agent Fluffball, The Incredible Feline
Animal: Dog
Names: Ruff the Protector, Wonder Canine, Sir Barks-a-Lot
Animal: ${capitalizedAnimal}
Names:`;
}
It's the default export of a file. So when it is imported in another file, the whole default export can be placed into a variable.
// file1.js
export default async function (req, res) {
...
}
// file2.js
import myDefault from "file1.js";
// do something with myDefault
Or using the alternative syntax, useful when there are other exports from the file:
// file3.js
import { default as alias } from "file1.js";
// do something with alias
Function in question is an default export of the file, so when this file will be imported you will be able to give this default export any name, e.g. import defaultExportAlias from "module-name";
Like this:
import func from './file';
func();
However keep in mind that unnamed exports are a violation of this eslint rule.

Cannot read property of undefined, Typescript

I'm having issues with creating a class function with optional parameters. I'm plagued with the following error and since I'm a new comer to typescript I'm not really sure as to what I have to change in my code to fix it. This code works perfectly fine in an earlier project written in JS only.
It specifically highlights the getRequestOptions, when I go check it in base-service.ts in the browser error.
08:32:12.755 client.ts:22 [vite] connecting...
08:32:13.067 client.ts:52 [vite] connected.
08:32:17.043 locales-service.ts:7 getting locales
08:32:17.048 base-service.ts:19 get /Api/GetLocales/ undefined undefined undefined
08:32:17.288 base-service.ts:21 Uncaught (in promise) TypeError: Cannot read properties of undefined (reading 'getRequestOptions')
at request (base-service.ts:21)
at getLocales (locales-service.ts:9)
at setup (locale-selector.vue:22)
at callWithErrorHandling (runtime-core.esm-bundler.js:6737)
at setupStatefulComponent (runtime-core.esm-bundler.js:6346)
at setupComponent (runtime-core.esm-bundler.js:6302)
at mountComponent (runtime-core.esm-bundler.js:4224)
at processComponent (runtime-core.esm-bundler.js:4199)
at patch (runtime-core.esm-bundler.js:3791)
at mountChildren (runtime-core.esm-bundler.js:3987)
And my code
base-service.ts
import axios from '#/plugins/axios'
export default class BaseService {
getRequestOptions(url:any, method:any, data?:any, params?:any , customHeaders?:any) {
const headers = {
...customHeaders
}
return {
url:url,
method:method,
data: data,
params: params,
headers: headers,
}
}
async request(method:any, url:any, data?:any, params?:any, headers?:any) {
console.log(method,url,data,params,headers)
const options = this.getRequestOptions(method, url, data, params, headers)
try {
console.log(options)
const response = await axios(options)
console.log("Getting response from api")
console.log(response)
if (response.status === 200) {
return response.data
}
} catch (error) {
console.log(error)
}
}
}
locales-service.ts
import BaseService from '../base-service'
//?Import models in the future
//import { } from '#/common/models'
class LocaleServ extends BaseService {
async getLocales() {
console.log("getting locales")
let result = await super.request(
'get',
'/Api/GetLocales/'
)
console.log(result)
return result
}
}
export const LocaleService = new LocaleServ()
Any help would be greatly appreciated
Edit:
<script lang="ts">
import { ref } from 'vue'
import { defineComponent } from 'vue'
import CountryFlag from 'vue-country-flag-next'
import { LocaleService } from '#/services'
export default defineComponent({
name: 'LocaleSelector',
components: {
CountryFlag
},
setup () {
const { getLocales } = LocaleService
const data = getLocales()
return {
data:data
}
}
})
</script>
And then in the component I call it with {{data}}
The issue lied in the way I called the destructured getLocales() method from LocaleService in locale-service.vue
I noticed that this was undefined after attaching a debugger. According to this article, destructuring it caused it to lose it's context. Therefore when I called getLocales() in base-service.ts, this was undefined.
Simple work around to fix the, caused due to inexperience, problem was to turn.
const { getLocales } = LocaleService
const data = getLocales()
into
const data = LocaleService.getLocales()

Module.exports in JavaScript

What is different between module.exports = testMethod ; and module.exports = { testMethod } ; Because when I am using module.exports = testMethod ; it is throwing error as below.
Error: Route.get() requires a callback function but got a [object Undefined]
But I am okay with module.exports = { testMethod } ;
Whole codes are
const testMethod = asyncErrorWrapper(async (req, res, next) => {
const information = req.body;
const question = await Question.create({
title: information.title,
content: information.content,
user: req.user.id,
});
res.status(200).json({
success: true,
data: question,
});
});
module.exports = { testMethod };
From VSCode, change between the ES5 or ES6 version to Js can take you on a bad way.
So, be carreful, i have the same problem recently, and after refactoring by use on ES6 module.exports = router to the end of some Js file (Node project using express) it was done.
Strange for me, on Cloud9 on Aws i have no problems.
Both are worked to export your module to outside function. But when you are using any callback function with
module.exports = somectrl
then it will fail but
module.exports = { somectrl }
because when you create an object, it actually instanciate it but when you pass a ref function/ const function name then it will behave as a existing function which does not work right.
you can do something like this to work,
module.exports = somectrl()
or
module.exports = new somectrl()

Refactoring probot event functions into seperate file causes error: TypeError: handler is not a function

I have the vanilla probot event function from the docs that comments on new issues:
const probotApp = app => {
app.on("issues.opened", async context => {
const params = context.issue({ body: "Hello World!" });
return context.github.issues.createComment(params);
});
}
This works fine.
I refactor the code into a separate file:
index.js
const { createComment } = require("./src/event/probot.event");
const probotApp = app => {
app.on("issues.opened", createComment);
}
probot.event.js
module.exports.createComment = async context => {
const params = context.issue({ body: "Hello World!" });
return context.github.issues.createComment(params);
};
But I receive this error:
ERROR (event): handler is not a function
TypeError: handler is not a function
at C:\Users\User\probot\node_modules\#octokit\webhooks\dist-node\index.js:103:14
at processTicksAndRejections (internal/process/task_queues.js:97:5)
at async Promise.all (index 0)
When I create a test as recommended in the docs with a fixture and mock the event webhook call with nock this works fine. But when I create a real issue on GitHub this error is thrown.
How can I refactor the code into a separate file without causing the error?
This was my mistake.
This is the whole probot.event.js file:
module.exports.createComment = async context => {
const params = context.issue({ body: "Hello World!" });
return context.github.issues.createComment(params);
};
module.exports = app => {
// some other event definitions
}
By defining module.exports = app I overwrote the previous module.export. The createComment function was therefore never exported.
Removing module.exports = app = { ... } fixed it!

Categories

Resources