vsphere-connect lib of nodejs - node.js

I am trying to use the same instance of a vsphere in many functions
Here is the lib vsphere-connect
const vSphereClient = vSphereConnect.createClient({
host: '',
username: '',
password: '',
ignoreSSL: true,
autoLogin: true,
exclusive: true,
})
Actually I got this.
exports.getVCenterInfo = function getVCenterInfo(req, res) {
!I would like to use an instance there!
}
I tried
vSphereClient.retrieve({ some code here})
Into my function but it doesn't work.
Can someone help me please ?

As i understand from the lib link you can't use it like this const vSphereClient = vSphereConnect.createClient({ because in vSphereClient you will get pending promise.
Maybe you will write lib named vsphereLib like this:
const connect = require('vsphere-connect');
let clientInstance;
connect.createClient({
host: 'vcenter.mydomain.com',
username: 'administrator#vsphere.local',
password: 'vmware1',
ignoreSSL: true,
autoLogin: true
})
.then(function (client) {
clientInstance = client;
});
module.exports = {
getClient: () => clientInstance,
};
Usage will be:
const client = require('./vsphereLib').getClient;
exports.getVCenterInfo = function getVCenterInfo(req, res) {
client()
.retrieve({
type: 'VirtualMachine',
id: ['vm-1234', 'vm-5678'],
properties: ['name', 'config.version']
})
.then(function (results) {
console.log(results);
})
.caught(function (err) {
console.log(err);
});
}
The only one problem is if connection will fail your code will fail aswell,so maybe you should extend vsphereLib with init function and run it before server starts

Related

How to create a Plaid LinkToken using Node JS?

I believe Plaid updated its createLinkToken documentation, but I can't seem to figure out what I'm doing wrong here. I'm taking a course, and here is the old code that worked in using a FirebaseFunction to create a link token with Plaid:
exports.createPlaidLinkToken = functions.https.onCall(async (data, context) => {
const customerId = context.auth.id;
const plaidClient = new plaid.Client({
clientID: functions.config().plaid.client_id,
secret: functions.config().plaid.secret,
env: plaid.environments.sandbox,
options: {
version: '2019-05-29',
},
});
return plaidClient.createLinkToken({
user: {
client_user_id: customerId,
},
client_name: "Bon Voyage",
products: ["auth"],
country_codes: ["US"],
language: "en"
}).then((apiResponse) => {
const linkToken = apiResponse.link_token;
return linkToken;
}).catch((err) => {
console.log(err);
throw new functions.https.HttpsError("internal", "Unable to create plaid link token: " + err);
});
});
I've tried a number of things. I know plaid.Client is now new.Configuration but I can't seem to figure out the rest. Any helpers?
You can see in the comments below what I've tried. I've modified the code as follows, and now receive Error status code 400.
const plaid = require('plaid');
const { Configuration, PlaidEnvironments, PlaidApi } = require("plaid");
exports.createPlaidLinkToken = functions.https.onCall(async (data, context) => {
const customerId = context.auth.uid;
const configuration = new Configuration({
basePath: PlaidEnvironments.sandbox,
baseOptions: {
headers: {
plaid_client_id: functions.config().plaid.client_id,
plaid_secret: functions.config().plaid.secret,
plaid_version: '2021-05-20'
},
},
});
const plaidClient = new PlaidApi(configuration);
return plaidClient.linkTokenCreate({
user: {
client_user_id: customerId,
},
client_name: "Bon Voyage",
products: ["auth"],
country_codes: ["US"],
language: "en"
})
.then((apiResponse) => {
const linkToken = apiResponse.data.link_token;
// const linkToken = response.link_token
return linkToken;
})
.catch((err) => {
console.log(err);
throw new functions.https.HttpsError(
"internal",
" Unable to create plaid link token: " + err
);
});
});
It's difficult to answer this question as you haven't mentioned what you've tried or what error you are experiencing. Have you reviewed the sample implementations in the docs that show how to do this, including the sample code in the Quickstart and Tiny Quickstart?
Off the top of my head, I do see that this sample code specifies an API version of 2019-05-29, which is not compatible with the latest version of the Node client library that uses new.Configuration.

How to test mongoose methods using sinon fakes?

I have the following arrangement of tests using sinon, mocha and chai:
type ModelObject = {
name: string;
model: typeof Categoria | typeof Articulo | typeof Usuario;
fakeMultiple: () => object[];
fakeOne: (id?: string) => object;
}
const models: ModelObject[] = [
{
name: 'categorias',
model: Categoria,
fakeMultiple: () => fakeMultiple({ creator: oneCategoria }),
fakeOne: oneCategoria
},
{
name: 'articulos',
model: Articulo,
fakeMultiple: () => fakeMultiple({ creator: oneArticulo }),
fakeOne: oneArticulo
},
{
name: 'usuarios',
model: Usuario,
fakeMultiple: () => fakeMultiple({ creator: oneUsuario }),
fakeOne: oneUsuario
}
];
const randomModel = models[Math.floor(Math.random() * models.length)];
describe(`v1/${randomModel.name}`, function () {
this.afterEach(function () {
sinon.restore();
});
context.only("When requesting information from an endpoint, this should take the Model of the requested endpoint and query the database for all the elements of that model", function () {
it.only(`Should return a list of elements of ${randomModel.name} model`, function (done) {
const fakes = randomModel.fakeMultiple();
const findFake = sinon.fake.resolves({ [randomModel.name]: fakes });
sinon.replace(randomModel.model, 'find', findFake);
chai.request(app)
.get(`/api/v1/${randomModel.name}`)
.end(
(err, res) => {
expect(res).to.have.status(200);
expect(res.body.data).to.be.an('object');
expect(res.body.data).to.have.property(randomModel.name);
expect(res.body.data[randomModel.name]).to.have.lengthOf(fakes.length);
expect(findFake.calledOnce).to.be.true;
done();
}
)
});
}}
I use this to test an endpoint that arbitrary returns information about a given model. In my controllers, I'm using a dynamic middleware to determine which model is going to be queried, for example, if the route consumed is "api/v1/categorias", it will query for Categorias model. If the route consumed is "api/v1/articulos", it will query for Articulos model, and so on.
To make the query, i use the following service:
import { Articulo } from '../models/articulo';
import { Usuario } from '../models/usuario';
import { Categoria } from '../models/categoria';
import logger from '../config/logging';
import { Model } from 'mongoose';
const determineModel = (model: string): Model<any> => {
switch (model) {
case 'articulos':
return Articulo;
case 'usuarios':
return Usuario;
case 'categorias':
return Categoria;
default:
throw new Error(`Model ${model} not found`);
}
};
export const getInformation = async (schema: string, page: number, limit: number) => {
try {
const model = determineModel(schema);
const data = await model.find().skip((page - 1) * limit).limit(limit);
const dataLength = await model.find().countDocuments();
return {
data,
total: dataLength,
};
} catch (err) {
logger.error(err);
console.log(err);
throw err;
}
};
The problem here lies when running my tests, it seems that is unable to run the .skip() and .limit() methods for my model.find()
error: model.find(...).skip is not a function
TypeError: model.find(...).skip is not a function
I think that I need to fake those methods, because when running the same test without skip and limit, it works as a charm. My problem lies in the fact that I don't know how to fake those, or to see if my guess is correct.
As a note, I have default params for the variables page and limit (1 and 15 respectively) so I'm not passing empty values to the methods.

I am getting a 500 response. Is the way I am trying this wrong? Or is there something I'm missing?

I'm making a game project. I have everything working to where you can create a character, and it posts okay to the database, and I can see the characters I've created on an endpoint with all the details included.
Where it doesn't work anywhere else is where I have things shifted from a context state to a separate context state for a 'character sheet' state. All the data successfully goes to my character sheet, and console.logs support everything is properly showing up, but it won't post to my url.
My model:
const mongoose = require("mongoose"),
Schema = mongoose.Schema;
const characterSheetSchema = new Schema({
characterPowers: {},
characterInventory: {},
characterArmor: {},
characterShield: {},
characterWeapon: {},
characterCoin: {},
characterHp: {},
characterStats: {},
characterExperience: { type: Number },
characterRace: {},
characterClass: {},
characterAge: {
type: Number,
},
characterName: {
type: String,
},
characterDescription: {
type: String,
},
characterLevel: { type: Number },
});
module.exports = CharacterSheet = mongoose.model(
"charactersheet",
characterSheetSchema
);
My routes:
const router = require('express').Router()
const CharacterSheet = require('../../models/chracterSheet/characterSheet.model')
router.post("/createcharactersheet", (req, res) => {
try {
let {
characterPowers,
characterInventory,
characterArmor,
characterShield,
characterWeapon,
characterCoin,
characterHp,
characterStats,
characterExperience,
characterRace,
characterClass,
characterAge,
characterName,
characterDescription,
characterLevel
} = req.body
const newCharacterSheet = new CharacterSheet({
characterPowers,
characterInventory,
characterArmor,
characterShield,
characterWeapon,
characterCoin,
characterHp,
characterStats,
characterExperience,
characterRace,
characterClass,
characterAge,
characterName,
characterDescription,
characterLevel
})
const savedCharacterSheet = newCharacterSheet.save()
res.json(savedCharacterSheet)
} catch (err) {
res.status(500).json({err: err.message})
}
})
router.get('/viewcharactersheets', (req, res) => {
CharacterSheet.find({}, function(err, charactersheets) {
if (err) {
console.log(err)
} else {
return res.json({charactersheets: charactersheets})
}
})
})
module.exports = router
My post request:
Axios.post("http://localhost:5000/characters/createcharactersheet", {
characterPowers: characterSheet.characterPowers,
characterInventory: characterSheet.characterInventory,
characterArmor: characterSheet.characterArmor,
characterShield: characterSheet.characterShield,
characterWeapon: characterSheet.characterWeapon,
chacterCoin: characterSheet.characterCoin,
characterHp: characterSheet.characterHp,
characterStats: characterSheet.characterStats,
characterExperience: characterSheet.characterExperience,
characterRace: characterSheet.characterRace,
characterClass: characterSheet.characterClass,
characterAge: characterSheet.characterAge,
characterName: characterSheet.characterName,
characterDescription: characterSheet.characterDescription,
characterLevel: characterSheet.characterLevel,
});
My Terminal
My error
POST error
Uncaught in promise error
Everything else works and goes into my restful api, but for a reason unknown to me, it won't post to my createcharactersheet document or api.
Any insight would be appreciated.
Mongoose Model.save() returns an Promise to try to use async/await
async/await way:
router.post("/createcharactersheet", async(req, res) => {
...
try {
const newCharacterSheet = new CharacterSheet({
...
})
await newCharacterSheet.save()
res.status(201).json(newCharacterSheet)
} catch (error) {
res.status(500).send(e.message)
{
})
or (im not sure)
const savedCharacterSheet = newCharacterSheet.save()
savedCharacterSheet
.then(saved =>
res.json(saved)
)
.catch(e =>
res.status(500).send(e.message)
)
Edit
Aslo log you errors
catch (e) {
console.error(e)
}

Knex pool full on migration

I'm trying to get started with knex.js and I can't get migrations to work. Knex works fine for my API calls. Here's my setup:
knexfile.js
const env = process.env;
module.exports = {
client: 'mysql',
connection: {
host: env.DB_HOST,
database: env.DB_NAME,
user: env.DB_USER,
password: env.DB_PASSWORD,
port: env.PORT
},
pool: {
min: 0,
max: 50
},
migrations: {
directory: './db/migrations',
tableName: 'knex_migrations'
},
seeds: {
directory: './db/seeds'
}
};
knex.js
const config = require('../knexfile.js');
module.exports = require('knex')(config);
events.js
const express = require('express');
const router = express.Router();
const knex = require('../../db/knex.js');
// GET api/events
router.get('/', (req, res) => {
knex('events')
.then(events => { res.send(events) }
.catch(err => { console.log(err); })
});
module.exports = router;
and then I have a file in the migrations folder with:
exports.up = function(knex) {
return knex.schema.createTable('users', function (t) {
t.increments('id').primary()
t.string('username').notNullable()
t.string('password').notNullable()
t.timestamps(false, true)
}).then(() => { console.log('created users table') })
.catch((err) => { throw err} )
.finally(() => { knex.destroy() })
};
exports.down = function(knex) {
return knex.schema.dropTableIfExists('users')
};
When I run knex migrate:latest I get TimeoutError: Knex: Timeout acquiring a connection. The pool is probably full. Are you missing a .transacting(trx) call?
I know similar questions have been asked before, but I can't seem to find any that shed light on my particular situation. I've tried adding a knex.destroy() to the end of my GET request but that doesn't seem to help (it just makes the connection unusable if I add other request handlers below).
I did try checking the knex.client.pool in a finally clause at the end of the GET request. numUsed was 0, numFree was 1, numPendingAcquires and numPendingCreates were both 0. I do find it odd that numFree was only 1 given that my knexfile specifies max 50. Any advice greatly appreciated.
Following #technogeek1995's comment, the answer turned out to be adding require('dotenv').config({path: '../.env'}); to knexfile.js (in retrospect, this part seems obvious), and running the cli from the same directory. Hope this helps someone else.

Node xmlbuilder mod TypeError: Converting circular structure to JSON

I'm trying to use the node xmlbuilder module, and copied / pasted their code from here but I get a
Converting circular structure to JSON error.
I have no clue why this is happening, here is the code:
Route:
app.get('/api/qb', function(req, res) {
qbwc.test(req, function(result){
res.send(result);
});
});
Module:
exports.test = function(data, next) {
var obj = {
person: {
name: "John",
'#age': 35,
address: {
city: "Istanbul"
},
phone: [
{
'#text': "555-1234",
'#type': 'home'
}, {
'#text': "555-1235",
'#type': 'mobile'
}
],
id: function() {
return 42;
}
}
};
var root = builder.create(obj);
return next(root);
}
EDIT:
I also tried it with something very simple to test, same issue:
var obj = { name: 'smith'};
var root = builder.create(obj);
return next(root);
Ok so after a lot of hair pulling, it seems you need to call .end() on the process, I have no idea why they don't have this in the example.
Here is what you need to do:
...
var root = builder.create(obj);
root = root.end({pretty: false});
return next(root);

Resources