react getting an error when posting to MS SQL database - sql-server

I'm trying to POST a record to my MS SQL database and I'm getting an Internal Server Error status of 500 which is the response programmed in the api:
exports.create = (req, res) => {
// Save Budget to MSSQL database
Budgets.create({
clientid: req.body.clientid,
catitem: req.body.catitem,
subcatitem: req.body.subcatitem,
startDate: req.body.startDate,
endDate: req.body.endDate,
quantity: req.body.quantity,
frequency: req.body.frequency,
cost: req.body.cost
}).then(budget => {
// Send created budget to budget
res.send(budget);
}).catch(err => {
res.status(500).send("Error -> " + err);
})
};
Here is the code for posting the record from the client:
export const createBudget = (budgetData = {
clientid: null,
catitem: '',
subcatitem: '',
startDate: '',
endDate: '',
quantity: '',
frquency: '',
cost: ''
}) => {
return (dispatch) => {
const budget = {
clientid: budgetData.clientid,
catitem: budgetData.catitem,
subcatitem: budgetData.subcatitem,
startDate: budgetData.startDate,
endDate: budgetData.endDate,
quantity: budgetData.quantity,
frequency: budgetData.frequency,
cost: budgetData.cost
};
return axios.post('budgets/create', budget).then(result => {
dispatch(_createBudget(result.data));
});
};
};
Initially this worked with with just four columns in the table (clientid, catitem, subcatitem, and cost) but I had to add extra columns and now it dosen't work. When I click the link shown in Developer Tools I get a page that states: "Cannot GET /api/budgets/create" yet the route defined in the api is: "app.post('/api/budgets/create', budgets.create);"
Is the "Cannot GET /api/budgets/create" the typical response for a failure to a post or is there something else going on? And how do I determine what the root cause is for the failure? Also I can INSERT a record into the table using Azure Data Studio with a SQL statement (developing on a Mac).

So after further analysis I discovered that I had to manually add the fields createdAt and updatedAt (required by Axios) to the database table then restart the Docker MS Sql service. Everything now works. What tipped me off to this solution was noticing and examining the initial get of the Budgets table and that's what was failing and therefor the failing of the POST request.

Related

AxiosError when integrating Stripe with Next.js

I am relatively new to Next.js, and I though I have been encountering some bugs and issues here and there, I have been able to overcome most of them. The latest one I have not been able to figure out, so let's see if somebody else knows what's going on.
I am creating an e-commerce platform on Next.js, Redux and Axios. For the moment I am using fake data to populate the products. When creating a checkout session, the data of the items in the cart is pushed (I can console.log() and I see the items in the terminal. However, the mapping of the checkout session to Stripe is not working. The error I get is an AxiosError: Request failed with status code 500
Error message screenshot
I am trying to add the item data dynamically to the checkout session as follows:
const stripe = require('stripe')(process.env.STRIPE_SECRET_KEY);
export default async (req, res) => {
const { items, email } = req.body;
const transformedItems = items.map((item) => ({
description: item.description,
// if quantities are bundled, this needs to change.
quantity: 1,
price_data: {
currency: 'usd',
unit_amount: item.price * 100,
product_data: {
name: item.title,
images: [item.image],
},
},
}));
const session = await stripe.checkout.sessions.create({
line_items: transformedItems,
mode: 'payment',
success_url: `${process.env.HOST}/success`,
cancel_url: `${process.env.HOST}/checkout`,
metadata: {
email,
images: JSON.stringify(items.map((item) => item.image)),
},
});
res.status(200).json({ id: session.id });
};
I have also tried copying the exact code from the Stripe documentation and implementing the changes, but this hasn't changed anything either.
I know, Stripe has made some changes to their API, and that for instance you can't specify anymore with statements like
payment_method_types: ["card"],
anymore. So I took it out.
I have not included any code from the checkout piece, as this seems to be working (as stated, it console.logs() just fine. I can provide this as well though, if someone thinks the issue might be there.
Thanks in advance.
Nela.
Thanks to Code-Apprentice and maiorano84 whose hints in the comments:
A status code 500 means there is an error on the backend. If the server is under your control, then you need to look at the server logs to see what the problem is. The server logs will have a stack trace that shows you where the problem occurs. If you need help understanding the stacktrace, you will need to include it in your question. – Code-Apprentice 22 hours ago
Is this a server-side or client-side AJAX request? If it's the latter, check your network tab to see the full output of your failed request (marked in red in Chrome Devtools). You should be able to get more information about the failed request there. If it's failing on the Stripe side, the Response Headers and Body should have more information there to help you debug. If it's failing on your own success and checkout callbacks, your server logs might have additional information that can help you. – maiorano84 22 hours ago
led me to the answer. I checked my console, and the error that was given was from Stripe. It read as follows:
StripeInvalidRequestError: You cannot use line_items.amount, line_items.currency, line_items.name, line_items.description, or line_items.images in this API version. Please use line_items.price or line_items.price_data.
So I moved the item.description I had outside of the product_data object, into it, and it worked.
The code looks now like this:
const stripe = require('stripe')(process.env.STRIPE_SECRET_KEY);
export default async (req, res) => {
const { items, email } = req.body;
const transformedItems = items.map((item) => ({
// if quantities are bundled, this needs to change.
quantity: 1,
price_data: {
currency: 'usd',
unit_amount: item.price * 100,
product_data: {
name: item.title,
description: item.description,
images: [item.image],
},
},
}));
const session = await stripe.checkout.sessions.create({
line_items: transformedItems,
mode: 'payment',
success_url: `${process.env.HOST}/success`,
cancel_url: `${process.env.HOST}/checkout`,
metadata: {
email,
images: JSON.stringify(items.map((item) => item.image)),
},
});
res.status(200).json({ id: session.id });
};

SequelizeDatabaseError Data truncated for column position at row 4

I am getting a SequelizeDatabaseError Data truncated for column 'position' at row 4 while sending an update request as below: Any advise on how to fix the database error ?
Executing (default): UPDATE user SET photo=?,name=?,email=?,phonenumber=?,position=?,password=?,updatedAt=? WHERE email = ?
SequelizeDatabaseError: Data truncated for column 'position' at row 4
at Query.formatError (C:\Project\soccerpep\node_modules\sequelize\lib\dialects\mysql\query.js:244:16)
at Execute.handler [as onResult] (C:\Project\soccerpep\node_modules\sequelize\lib\dialects\mysql\query.js:51:23)
module.exports = function(sequelize, DataTypes) {
return sequelize.define('user', {
name: {
type: DataTypes.STRING(30),
allowNull: false
},
email: {
type: DataTypes.STRING(100),
allowNull: false
},
phonenumber: {
type: DataTypes.STRING(50),
},
id: {
type: DataTypes.INTEGER(10).UNSIGNED,
allowNull: false,
primaryKey: true,
autoIncrement: true
},
password: {
type: DataTypes.STRING(50),
allowNull: false
},
privilege: {
type: DataTypes.ENUM('PLAYER','ADMIN'),
},
photo: {
type: DataTypes.STRING(30),
},
position: {
type: DataTypes.ENUM('FORWARD','MID-FIELD','DEFENDER','GK'),
}
}, {
tableName: 'user'
});
};
server.js
const UserModel = userSchema(sequelize, DataTypes);
app.put('/service/profile', async (req, res, next) => {
try {
const userEmail = req.query.email;
var selector = {
where: { email: userEmail }
};
const updatePlayer = await UserModel.update(req.body, selector);
console.log("Server side update method log:" + updatePlayer);
res.status(200).json({ success: true });
} catch (err) {
return next(err);
}
});
I think the issue is with ENUM, you can use that only with Postgres and not with mysql , ( Ref )
position: {
type: DataTypes.ENUM('FORWARD','MID-FIELD','DEFENDER','GK'),
}
Change it to simple string type and check again,
position: {
type: DataTypes.STRING(30)
}
NOTE : You might need to create table again or update the field
manually after changing this in model else you will still get the
error
If you want to use ENUMs in mysql you should use it as so
position: {
type: DataTypes.ENUM,
values: ['player', 'admin],
defaultValue: 'monthly' // A default value just incase you fail to provide one...
},
I do hope this helps...
Change datatype is not the solution. You have to check the data that you try to save. eg: if ENUM("0", "1") and you try to saved data 0 then it's showing that type of error. You have to save like that "0". Then it's not showing such type of error message again.
i have a lot spending my day to tracing this error.
i have following all solution but doesnt work.
in my case and my bad is...
i forgot have clone table/duplicate/history/trigger that save old and new data.
make sure your history table have same data type.
i have table like these
form3
hs_form3 // its mean history with revision (number of revisi data) column and action column (create/update/delete/any)
just for description
CREATE TABLE hs_form3 LIKE form3;
ALTER TABLE hs_form3 MODIFY COLUMN id int(11) NOT NULL,
DROP PRIMARY KEY, ENGINE = InnoDB, ADD action VARCHAR(8) DEFAULT 'insert' FIRST,
ADD revision INT(6) NOT NULL AUTO_INCREMENT AFTER action,
ADD dt_datetime DATETIME NOT NULL DEFAULT CURRENT_TIMESTAMP AFTER revision,
ADD PRIMARY KEY (revision),
ADD KEY `user_id` (`user_id`),
and i didnt run migration on server because a lot of change , i only run on localhost. in server i just put a new table by export import or added manual. before i got issue about migration on server and doesnt capture last change in sql table and dont have time to resolve.

react-native-gifted-chat showing same message multiple time

I'm using react-native-gifted-chat in my react-native app. As I shown in this image, there is same message displayed multiple time and message: Yes getting new msg 's place is also varied from it's actual position.
My issue is same as this. Can anyone please help me to solve this.
Thank you in advance.
I got a solution of my question. #Ron you are right but in my case the issue is different. I solved it by change my format of parameters. It took different format and I passed different so they conflicted each other. Here is the solution it may useful to others.
parse = snapshot => {
const { timestamp: numberStamp, text } = snapshot.val();
const { key: _id } = snapshot;
const createdAt = moment(snapshot.val().createdAt, "DD/MM/YYYY hh:mm:ss");
const user = { };
var temp_data = snapshot.val()
if(snapshot.val().name == this.state.temp_logged_name) {
user._id = 1;
user.name = temp_data.name;
user.avatar = temp_data.avatar;
}
const message = {
_id,
createdAt,
text,
user,
};
return message;
};
I had encountered this issue as well. I had set up react-native-gifted-chat on my mobile app. And at the other end I had set up a simple HTML page with a script to initialise the Websocket connection and send messages on the onsend event. What I had realised later that while the unique id was getting generated at the app end (because the id was being generated by the library itself), nothing of such sort existed at the other end.
Basically, this weird behaviour crops up when a unique id _id is missing for a message. Each message must have at least the following properties while executing GiftedChat.append(previousMessages, messages).
{
_id: 1,
text: 'Hello developer',
createdAt: new Date(),
user: {
_id: 2
}
}
There could be two reasons behind it,
1) Each message should be passed a unique id, so just use uuidv4 npm package and append it to _id prop of the object.
Example:
messages: GiftedChat.append(previousState.messages, {
_id: uuidv4(), // or use Math.round(Math.random() * 1000000)
text: text,
createdAt: new Date(),
user: {
_id: 2,
name: "React Native",
avatar: "https://placeimg.com/140/140/any"
},
image: attachment
})
2) Second possibility could be on the gateway you are using to initiate the chat between users. So, some gateways have known issues to repeat the message multiple times. You could to string comparison each time a new message is received and pushed to the chat screen, however it is not advised to do this.
I figured this out by simply applying the filter to the incoming message in useLayout Effect:
useLayoutEffect(() => {
db.collection('Chats').doc(docID).collection('messages').orderBy("createdAt", "desc").onSnapshot(snapshot => {
setMessages(
prev =>
prev
.filter((ftr,index,self) => ftr?.user?._id !== loginUser?.id) //login user id is the current user's id you can do the same for recieved messages
.concat
(snapshot.docs.map(doc => doc.data({
_id: doc?.id,
user: doc.data().user,
text: doc.data().text,
createdAt:new Date(doc.data().createdAt),
})
))
)
})
},[])
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/16.6.3/umd/react.production.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/16.6.3/umd/react-dom.production.min.js"></script>

How do I get Sails.js to query an existing database?

There's a dev database already set up for another project. I'm trying to create a sails.js server to connect to this database and act as a RESTful API. I'm also using SQL Workbench with the profile below to connect to the database and verify my query statements. On that tool, I'm able to send queries like select top 10 * from advisor and get the data I expect in response.
My connection configuration in sails.js seems to be alright, since I'm able to start the server. I've gotten simple static actions to work, like hi: function (req, res) { return res.send("Hi there!"); }. However, I can't figure out what to do to get a response from the database served by sails. My goal (at this point) is to have http://localhost:1337/advisor return JSON for the results of select top 10 * from advisor.
I initially tried using the freshly-generated model. Then, I tried adding attributes to the model file. Then, I tried adding my own code to the controller. In each case, the browser never received a response. At the end, I tested /advisor/list to run my own code and it doesn't look like the query() callback was ever executed. In case it's the first question, I have run npm install sails-sqlserver and I've double-checked that my host, db, username, & password are identical to what was used in Workbench.
connections.js
sqlserver: {
adapter: 'sails-sqlserver',
user: 'myusername',
password: 'mypassword',
host: 'mysubdomain.mydomain.net:1433',
database: 'frontofficedev'
}
models.js
module.exports.models = {
connection: 'sqlserver',
migrate: 'safe'
};
api\models\Advisor.js
module.exports = {
attributes: {
advcode: 'string',
advname: 'string',
'adv-default': 'boolean',
"user-id": 'string',
"pc-code": 'string',
"adv-tag": 'string',
"is-group": 'boolean',
"trade-grouping": 'string',
AdvisorId: 'int',
orgcode: 'string',
BranchId: 'int',
OrdPrnBranchId: 'int',
zdec1: 'float',
zdec2: 'float',
zchar1: 'string',
zchar2: 'string',
zchar3: 'string',
zchar4: 'string',
AdvStatus: 'string'
}
};
api\controllers
module.exports = {
hi: function (req, res) {
return res.send("Hi there!");
},
list: function (req, res) {
var myQuery = "select TOP 10 * from advisor";
sails.log.debug("Query :", myQuery);
console.log(Advisor);
Advisor.query(myQuery, function (err, advisors){
console.log(advisors);
console.log(err);
if(err || !advisors.rows.length){
return res.json({"status": 0, "error": err});
}
else{
return res.json(advisors);
}
});
}
};
Any ideas on what I'm doing wrong? Is JDBC causing problems? Thanks in advance.
Im assuming you've already run: npm install sails-sqlserver --save
You have to specify your connection and the table you will be using in the model, the variables in the model should match with your DB variables, like this:
api\models\Advisor.js
module.exports = {
schema: true,
connection: 'sqlserver',
tableName: 'yourTableName',
attributes: {
advcode:{
type: 'string',
primaryKey: true //if this is a primary key
},
advname:{
type: 'string'
},
'adv-default':{
type: 'boolean'
}
};
In your controller you can use the Sails ORM waterline like this:
api\controllers
module.exports = {
list: function (req, res) {
Advisor.query('SELECT * FROM advisor', function(err, results) {
if (err) {
res.send(400);
} else {
res.send(results);
}
});
}
};
Where Advisor is the model.
For more specific information about models and ORM waterline i recommend you read the sails docs: http://sailsjs.org/documentation/reference/waterline-orm/models
My colleague spotted the problem. The port that database lives on needs to be a separate attribute in sails' connection.js (instead of including it in the host string). No need for extra libraries, like node-jdbc.
config/connections.js
sqlserver: {
adapter: 'sails-sqlserver',
user: 'myusername',
password: 'mypassword',
host: 'mysubdomain.mydomain.net',
port: 1433,
database: 'frontofficedev'
}
After making that change, I was able to delete all my custom code from the controller and almost everything from the model (I still need to specify a primary key, since sails looks for id by default and the database was using AdvisorId.
api/models/Advisor.js
module.exports = {
attributes: {
AdvisorId: {primaryKey: true}
}
};

Connecting NodeJS Express to MS SQL Server

I'm a NodeJS newbie and I am building an application that talks to an MSSQL (SQL Server 2008 R2) Database. For this, I tried using Sequelize, an ORM library that claims to do so.
While I have been successful in making it work with MySQL, SQL Server connection is just not working. I connected to a local database on both the occasions. Here's what I tried (as given in the docs):
[Part 1: Establish Connection]
... Express Code ...
var Sequelize = require('sequelize');
var sequelize = new Sequelize('NewDB', '', '', {
host: '(localdb)\v11.0',
dialect: 'mssql',
pool: {
max: 5,
min: 0,
idle: 10000
}
});
[Part 2: Testing]
var User = sequelize.define('user', {
firstName: {
type: Sequelize.STRING,
field: 'first_name' // Will result in an attribute that is firstName when user facing but first_name in the database
},
lastName: {
type: Sequelize.STRING
}
}, {
freezeTableName: true // Model tableName will be the same as the model name
});
User.sync({force: true}).then(function () {
// Table created
return User.create({
firstName: 'John',
lastName: 'Hancock'
});
});
... Express Code ...
The database NewDB does exist on the server. Now, While using SQL Server Express, the same credentials work. But not here. The error that I see is:
Unhandled rejection SequelizeConnectionError: Failed to connect to (localdb)\v11.0:1433 = getaddrinfo ENOTFOUND (localdb)\v11.0
So, here's the question. What credentials do I put, so that it works? And if it doesn't what would be alternate library to establish a Database connection? I'll prefer an ORM, but it's not that important a thing (anything works as long as I can connect to the DB).

Resources