Identifying Mongoose schema validation errors as HTTP status codes - keystonejs

I'm leveraging Keystone.js to provide a lightweight CMS and API. I'm checking for duplicate entries on a List as such:
Registration.schema.post('save', function(error, registration, next) {
if (error && error.name === 'MongoError' && error.code === 11000) {
error = Error(`409|${ registration['email'] } is already registered`);
}
next(error);
});
I'm parsing the status code off the error message to return in my API endpoint.
Is there a different way to provide a friendly error message for duplicates in Keystone admin and be able to return the correct status code for API calls?

as db version v3.6.9
$ mongod --version
db version v3.6.9
git version: 167861a164723168adfaaa866f310cb94010428f
OpenSSL version: OpenSSL 1.0.1t 3 May 2016
allocator: tcmalloc
modules: none
build environment:
distmod: debian81
distarch: x86_64
target_arch: x86_64
I think you should check for ValidationError property instead MongoError as below:
RegistrationSchema.create(obj)
.then(...)
.catch(err => console.error('[registration] output: ', err);
We'll suppose the email is not mentioned before to simulate an is required error.
You'll see like that:
[registration] error: { ValidationError: Registration validation failed: email: Path `email` is required.
at ValidationError.inspect (....)
errors:
{
email:
{ Path `email` is required.
...
message: 'Path `email` is required.',
name: 'ValidatorError',
properties: [Object],
kind: 'required',
path: 'email',
value: [],
reason: undefined,
'$isValidatorError': true } },
_message: 'Registration validation failed',
name: 'ValidationError' }

Related

How to a pass a complex object as a mock data service stub

I'm working on a test for a module, which works except for the fact that I can not access, the inner object attributes properties.
tokenStorageServiceStub = { // Mock service data
getUser: () => of({
username: 'organization-a-a-normal',
roles: ['PROCESSOR'],
attributes: {
organizationId: 111,
organizationName: 'Org.name Aa',
userFullName: 'User for organization A-A',
userId: 22,
},
access_token: 'AT01',
refresh_token: 'RT01',
token_type: 'Bearer',
expires_in: 3600,
}),
};
The component code complains about the last statement:
this.activeTokens = this.token.getUser(); // OK
this.username = this.activeTokens.username; // OK
this.organization.id = this.activeTokens.attributes.organizationId; // `attributes` is undefined?
Chrome Headless 88.0.4298.0 (Linux x86_64) SettingsComponent should create FAILED
TypeError: Cannot read property 'organizationId' of undefined
at SettingsComponent.call [as ngOnInit] (src/app/organization/settings/settings.component.ts:22:61)
I think it's because of the innerworking of the RxJs.of() function. In the manual, I see things like ObservableInput. But there is no mention of Objects as such.
I also read about of() getting deprecated? What will be a good approach to pass my object data in a test service stub?

Unable to log in to CDK created Amazon MQ (RabbitMQ) web console

When creating a publicly accessible Amazon MQ instance (with RabbitMQ under the hood), I can easily log in to the web console.
However when creating an MQ instance using the same settings and credentials through CDK I can't log in to the web console. The only response from the RabbitMQ service is
{
"error": "not_authorised",
"reason": "Login failed"
}
The Cloudwatch logs indicate that the user was created, but also warn that the user tried to log in using invalid credentials:
2021-07-02 14:20:54.867 [info] <0.1474.0> Created user 'admin'
2021-07-02 14:20:55.587 [info] <0.1481.0> Successfully set user tags for user 'admin' to [administrator]
2021-07-02 14:20:56.295 [info] <0.1488.0> Successfully set permissions for 'admin' in virtual host '/' to '.*', '.*', '.*'
2021-07-02 14:26:14.529 [warning] <0.1639.0> HTTP access denied: user 'admin' - invalid credentials
The construction of the Broker looks like this:
private createMessageBroker(vpc: Vpc, stage: Stage) {
const password: Secret = new Secret(this, 'BrokerAdminPassword', {
generateSecretString: { excludePunctuation: true },
description: 'Password for the Message Broker User',
});
const user: CfnBroker.UserProperty = {
consoleAccess: true,
username: 'admin',
password: password.toString(),
};
new CfnBroker(this, 'TaskMessageBroker', {
autoMinorVersionUpgrade: true,
brokerName: 'MessageBroker',
deploymentMode: 'SINGLE_INSTANCE',
engineType: 'RABBITMQ',
engineVersion: '3.8.11',
hostInstanceType: 'mq.t3.micro',
publiclyAccessible: true,
users: [user],
logs: { general: true },
});
}
Try using the following instead when instantiating your UserProperty
const user: CfnBroker.UserProperty = {
consoleAccess: true,
username: 'admin',
password: password.secretValue.toString(),
}

Nodemailer SES TRANSPORT Error: "UnexpectedParameter: Unexpected key 'Destination' found in params"

Facing issue while sending AWS SES Templated email using SES TRANSPORT from Nodemailer.
In SES TRANSPORT Documentation, it says
To use SES transport, set a aws.SES object as the value for SES property in Nodemailer transport options.
Here's how my code looks.
transporter.sendMail({
ses: {
Destination: {
CcAddresses: [],
ToAddresses: 'recipient#example.com'
},
Source: 'sender#example.com' ,
Template: 'template_name' ,
TemplateData: JSON.stringify(data) ,
// optional extra arguments for SendRawEmail
Tags: [{
Name: 'tag name',
Value: 'tag value'
}]
}
}, (err, info) => {
console.log(info.envelope);
console.log(info.messageId);
});
This is the error I am getting.
2019-08-12T17:03:38.210Z error: There were 3 validation errors:
* UnexpectedParameter: Unexpected key 'Destination' found in params
* UnexpectedParameter: Unexpected key 'Template' found in params
* UnexpectedParameter: Unexpected key 'TemplateData' found in params

Invalid CSRF when logging in to keystone

I'm entirely new to coding. I've looked around a bit, but not found anything relevant.
When logging into keystone to view our mongoDB database I get an error message saying:
Something went wrong; please refresh your browser and try again.
Doing that does not help. Neither does deleting the browser history or attempting from another lap top.
Looking at the javascript console in the browser, the error states invalid csrf.
I think this is the relevant source code in the keystone folder:
handleSubmit (e) {
e.preventDefault();
// If either password or mail are missing, show an error
if (!this.state.email || !this.state.password) {
return this.displayError('Please enter an email address and password to sign in.');
}
xhr({
url: `${Keystone.adminPath}/api/session/signin`,
method: 'post',
json: {
email: this.state.email,
password: this.state.password,
},
headers: assign({}, Keystone.csrf.header),
}, (err, resp, body) => {
if (err || body && body.error) {
return body.error === 'invalid csrf'
? this.displayError('Something went wrong; please refresh your browser and try again.')
: this.displayError('The email and password you entered are not valid.');
} else {
// Redirect to where we came from or to the default admin path
if (Keystone.redirect) {
top.location.href = Keystone.redirect;
} else {
top.location.href = this.props.from ? this.props.from : Keystone.adminPath;
}
}
});
},
How can I go about solving this / debugging the error? Thanks for any help!
This usually happens when session affinity fails. Are you using default in-memory session management? Maybe, try using a database for maintaining session state.
If you use MongoDB, Try the following config setting
'session store': 'mongo',
See 'session store' section under http://keystonejs.com/docs/configuration/#options-database for more details.

sails-rabbitmq adapter integration with mongodb issue

I have setup a sailsjs project and trying to access rabbitmq using sails-rabbitmq adapter. I have followed https://www.npmjs.com/package/sails-rabbitmq .
I want to use mongodb with rabbitmq. problem is when i 'sails lift' i get this error.
error: A hook (orm) failed to load!
error: Error: One of your models (message) refers to multiple datastores.
Please set its configured datastore to a string instead of an array in its model definition (.connection) or the app-wide default (sails.config.models.connection)
(this is conventionally set in your config/models.js file, or as part of your app's environment-specific config).
at constructError (C:\Users\demoapp\AppData\Roaming\npm\node_modules\sails\node_modules\sails-hook-orm\lib\construct-error.js:57:13)
at validateModelDef (C:\Users\demoapp\AppData\Roaming\npm\node_modules\sails\node_modules\sails-hook-orm\lib\validate-model-def.js:97:11)
at C:\Users\demoapp\AppData\Roaming\npm\node_modules\sails\node_modules\sails-hook-orm\lib\initialize.js:218:36
at arrayEach (C:\Users\demoapp\AppData\Roaming\npm\node_modules\sails\node_modules\lodash\index.js:1289:13)
at Function.<anonymous> (C:\Users\demoapp\AppData\Roaming\npm\node_modules\sails\node_modules\lodash\index.js:3345:13)
at Array.async.auto._normalizeModelDefs (C:\Users\demoapp\AppData\Roaming\npm\node_modules\sails\node_modules\sails-hook-orm\lib\initialize.js:216:11)
at listener (C:\Users\demoapp\AppData\Roaming\npm\node_modules\sails\node_modules\sails-hook-orm\node_modules\async\lib\async.js:605:42)
at C:\Users\demoapp\AppData\Roaming\npm\node_modules\sails\node_modules\sails-hook-orm\node_modules\async\lib\async.js:544:17
at _arrayEach (C:\Users\demoapp\AppData\Roaming\npm\node_modules\sails\node_modules\sails-hook-orm\node_modules\async\lib\async.js:85:13)
at Immediate.taskComplete (C:\Users\demoapp\AppData\Roaming\npm\node_modules\sails\node_modules\sails-hook-orm\node_modules\async\lib\async.js:543:13)
at processImmediate [as _immediateCallback] (timers.js:383:17)
I have > connection: [ 'rabbitCluster', 'regularMongo' ]
in my Message model. regularMongo is mongodb connection. Please let me know what other configuration i am missing.
With following config I do not see any error. In sails.config.models set
module.exports.models = {
connection: 'someMongodbServer',
migrate: 'safe'
};
in Message.js set
module.exports = {
connection: [ 'rabbitCluster', 'someMongodbServer' ],
routingKey: [ 'parentMessage' ],
attributes: {
title: 'string',
body: 'string',
parentMessage: {
model: 'message'
}
}
};