everything works?

This commit is contained in:
James
2020-11-20 17:12:39 -05:00
22 changed files with 250 additions and 218 deletions

View File

@@ -1,8 +1,8 @@
const jwt = require('jsonwebtoken');
const { AuthenticationError, LockedAuth } = require('../../errors');
const getCookieExpiration = require('../../utilities/getCookieExpiration');
const isLocked = require('../isLocked');
const removeInternalFields = require('../../utilities/removeInternalFields');
import jwt from 'jsonwebtoken';
import { AuthenticationError, LockedAuth } from '../../errors';
import getCookieExpiration from '../../utilities/getCookieExpiration';
import isLocked from '../isLocked';
import removeInternalFields from '../../utilities/removeInternalFields';
async function login(incomingArgs) {
const { config, operations } = this;

View File

@@ -6,6 +6,15 @@ require('@babel/register')({
/node_modules[\\/](?!@payloadcms[\\/]payload[\\/]src[\\/]admin|@payloadcms[\\/]payload[\\/]components|@payloadcms[\\/]payload[\\/]hooks).*/,
],
extensions: ['.js', '.jsx', '.ts', '.tsx'],
plugins: [
[
'babel-plugin-ignore-html-and-css-imports',
{
removeExtensions: ['.svg', '.css', '.scss', '.png', '.jpg'],
},
],
...babelConfig.plugins,
],
});
const payload = require('./index.ts');

View File

@@ -1,18 +1,15 @@
import nodemailer from 'nodemailer';
import logger from '../utilities/logger';
import mockHandler from './mockHandler';
logger();
async function buildEmail() {
if (!this.config.email.transport || this.config.email.transport === 'mock') {
logger.info('E-mail configured with mock configuration');
this.logger.info('E-mail configured with mock configuration');
const mockAccount = await mockHandler(this.config.email);
if (this.config.email.transport === 'mock') {
const { account: { web, user, pass } } = mockAccount;
logger.info(`Log into mock email provider at ${web}`);
logger.info(`Mock email account username: ${user}`);
logger.info(`Mock email account password: ${pass}`);
this.logger.info(`Log into mock email provider at ${web}`);
this.logger.info(`Mock email account username: ${user}`);
this.logger.info(`Mock email account password: ${pass}`);
}
return mockAccount;
}
@@ -30,7 +27,7 @@ async function buildEmail() {
try {
await email.transport.verify();
} catch (err) {
logger.error('There is an error with the email configuration you have provided.', err);
this.logger.error('There is an error with the email configuration you have provided.', err);
}
return email;

View File

@@ -7,4 +7,4 @@ class LockedAuth extends APIError {
}
}
module.exports = LockedAuth;
export default LockedAuth;

View File

@@ -6,4 +6,4 @@ class MissingCollectionLabel extends APIError {
}
}
module.exports = MissingCollectionLabel;
export default MissingCollectionLabel;

View File

@@ -6,4 +6,4 @@ class MissingFieldInputOptions extends APIError {
}
}
module.exports = MissingFieldInputOptions;
export default MissingFieldInputOptions;

View File

@@ -6,4 +6,4 @@ class MissingFieldType extends APIError {
}
}
module.exports = MissingFieldType;
export default MissingFieldType;

View File

@@ -7,4 +7,4 @@ class MissingFile extends APIError {
}
}
module.exports = MissingFile;
export default MissingFile;

View File

@@ -6,4 +6,4 @@ class MissingGlobalLabel extends APIError {
}
}
module.exports = MissingGlobalLabel;
export default MissingGlobalLabel;

View File

@@ -7,4 +7,4 @@ class NotFound extends APIError {
}
}
module.exports = NotFound;
export default NotFound;

View File

@@ -7,4 +7,4 @@ class ValidationError extends APIError {
}
}
module.exports = ValidationError;
export default ValidationError;

View File

@@ -1,15 +1,13 @@
import httpStatus from 'http-status';
import formatErrorResponse from '../responses/formatError';
import logger from '../../utilities/logger';
logger();
const errorHandler = (config) => async (err, req, res, next) => {
const errorHandler = (payload) => async (err, req, res, next) => {
const { config } = payload;
const data = formatErrorResponse(err);
let response;
let status = err.status || httpStatus.INTERNAL_SERVER_ERROR;
logger.error(err.stack);
payload.logger.error(err.stack);
if (config.debug && config.debug === true) {
data.stack = err.stack;
@@ -26,8 +24,7 @@ const errorHandler = (config) => async (err, req, res, next) => {
({ response, status } = await config.hooks.afterError(err, response) || { response, status });
}
res.status(status)
.send(response);
res.status(status).send(response);
};
export default errorHandler;

View File

@@ -1,11 +1,11 @@
import validations from '../validations';
import { email } from '../validations';
export default [
{
name: 'email',
label: 'Email',
type: 'email',
validate: validations.email,
validate: email,
admin: {
disabled: true,
},

View File

@@ -1,188 +1,218 @@
const defaultRichTextValue = require('./richText/defaultValue');
import defaultRichTextValue from './richText/defaultValue';
const defaultMessage = 'This field is required.';
const optionsToValidatorMap = {
number: (value, options = {}) => {
const parsedValue = parseInt(value, 10);
export const number = (value, options = {}) => {
const parsedValue = parseInt(value, 10);
if ((value && typeof parsedValue !== 'number') || (options.required && Number.isNaN(parsedValue))) {
return 'Please enter a valid number.';
}
if ((value && typeof parsedValue !== 'number') || (options.required && Number.isNaN(parsedValue))) {
return 'Please enter a valid number.';
}
if (options.max && parsedValue > options.max) {
return `"${value}" is greater than the max allowed value of ${options.max}.`;
}
if (options.max && parsedValue > options.max) {
return `"${value}" is greater than the max allowed value of ${options.max}.`;
}
if (options.min && parsedValue < options.min) {
return `"${value}" is less than the min allowed value of ${options.min}.`;
}
if (options.min && parsedValue < options.min) {
return `"${value}" is less than the min allowed value of ${options.min}.`;
}
if (options.required && typeof parsedValue !== 'number') {
return defaultMessage;
}
return true;
},
text: (value, options = {}) => {
if (options.maxLength && (value && value.length > options.maxLength)) {
return `This value must be shorter than the max length of ${options.max} characters.`;
}
if (options.minLength && (value && value.length < options.minLength)) {
return `This value must be longer than the minimum length of ${options.max} characters.`;
}
if (options.required) {
if (typeof value !== 'string' || (typeof value === 'string' && value.length === 0)) {
return defaultMessage;
}
}
return true;
},
password: (value, options = {}) => {
if (options.maxLength && value.length > options.maxLength) {
return `This value must be shorter than the max length of ${options.max} characters.`;
}
if (options.minLength && value.length < options.minLength) {
return `This value must be longer than the minimum length of ${options.max} characters.`;
}
if (options.required && !value) {
return defaultMessage;
}
return true;
},
email: (value, options = {}) => {
if ((value && !/\S+@\S+\.\S+/.test(value))
|| (!value && options.required)) {
return 'Please enter a valid email address.';
}
return true;
},
textarea: (value, options = {}) => {
if (options.maxLength && value.length > options.maxLength) {
return `This value must be shorter than the max length of ${options.max} characters.`;
}
if (options.minLength && value.length < options.minLength) {
return `This value must be longer than the minimum length of ${options.max} characters.`;
}
if (options.required && !value) {
return defaultMessage;
}
return true;
},
wysiwyg: (value, options = {}) => {
if (options.required && !value) {
return defaultMessage;
}
return true;
},
code: (value, options = {}) => {
if (options.required && value === undefined) {
return defaultMessage;
}
return true;
},
richText: (value, options) => {
if (options.required) {
const stringifiedDefaultValue = JSON.stringify(defaultRichTextValue);
if (value && JSON.stringify(value) !== stringifiedDefaultValue) return true;
return 'This field is required.';
}
return true;
},
checkbox: (value, options = {}) => {
if ((value && typeof value !== 'boolean')
|| (options.required && typeof value !== 'boolean')) {
return 'This field can only be equal to true or false.';
}
return true;
},
date: (value, options = {}) => {
if (value && !isNaN(Date.parse(value.toString()))) { /* eslint-disable-line */
return true;
}
if (value) {
return `"${value}" is not a valid date.`;
}
if (options.required) {
return defaultMessage;
}
return true;
},
upload: (value, options = {}) => {
if (value || !options.required) return true;
if (options.required && typeof parsedValue !== 'number') {
return defaultMessage;
},
relationship: (value, options = {}) => {
if (value || !options.required) return true;
return defaultMessage;
},
array: (value, options = {}) => {
if (options.minRows && value < options.minRows) {
return `This field requires at least ${options.minRows} row(s).`;
}
}
if (options.maxRows && value > options.maxRows) {
return `This field requires no more than ${options.maxRows} row(s).`;
}
if (!value && options.required) {
return 'This field requires at least one row.';
}
return true;
},
select: (value, options = {}) => {
if (Array.isArray(value) && value.find((input) => !options.options.find((option) => (option === input || option.value === input)))) {
return 'This field has an invalid selection';
}
if (typeof value === 'string' && !options.options.find((option) => (option === value || option.value === value))) {
return 'This field has an invalid selection';
}
if (options.required && !value) {
return defaultMessage;
}
return true;
},
radio: (value, options = {}) => {
const stringValue = String(value);
if ((typeof value !== 'undefined' || !options.required) && (options.options.find((option) => String(option.value) === stringValue))) return true;
return defaultMessage;
},
blocks: (value, options) => {
if (options.minRows && value < options.minRows) {
return `This field requires at least ${options.minRows} row(s).`;
}
if (options.maxRows && value > options.maxRows) {
return `This field requires no more than ${options.maxRows} row(s).`;
}
if (!value && options.required) {
return 'This field requires at least one row.';
}
return true;
},
return true;
};
export default optionsToValidatorMap;
export const text = (value, options = {}) => {
if (options.maxLength && (value && value.length > options.maxLength)) {
return `This value must be shorter than the max length of ${options.max} characters.`;
}
if (options.minLength && (value && value.length < options.minLength)) {
return `This value must be longer than the minimum length of ${options.max} characters.`;
}
if (options.required) {
if (typeof value !== 'string' || (typeof value === 'string' && value.length === 0)) {
return defaultMessage;
}
}
return true;
};
export const password = (value, options = {}) => {
if (options.maxLength && value.length > options.maxLength) {
return `This value must be shorter than the max length of ${options.max} characters.`;
}
if (options.minLength && value.length < options.minLength) {
return `This value must be longer than the minimum length of ${options.max} characters.`;
}
if (options.required && !value) {
return defaultMessage;
}
return true;
};
export const email = (value, options = {}) => {
if ((value && !/\S+@\S+\.\S+/.test(value))
|| (!value && options.required)) {
return 'Please enter a valid email address.';
}
return true;
};
export const textarea = (value, options = {}) => {
if (options.maxLength && value.length > options.maxLength) {
return `This value must be shorter than the max length of ${options.max} characters.`;
}
if (options.minLength && value.length < options.minLength) {
return `This value must be longer than the minimum length of ${options.max} characters.`;
}
if (options.required && !value) {
return defaultMessage;
}
return true;
};
export const wysiwyg = (value, options = {}) => {
if (options.required && !value) {
return defaultMessage;
}
return true;
};
export const code = (value, options = {}) => {
if (options.required && value === undefined) {
return defaultMessage;
}
return true;
};
export const richText = (value, options) => {
if (options.required) {
const stringifiedDefaultValue = JSON.stringify(defaultRichTextValue);
if (value && JSON.stringify(value) !== stringifiedDefaultValue) return true;
return 'This field is required.';
}
return true;
};
export const checkbox = (value, options = {}) => {
if ((value && typeof value !== 'boolean')
|| (options.required && typeof value !== 'boolean')) {
return 'This field can only be equal to true or false.';
}
return true;
};
export const date = (value, options = {}) => {
if (value && !isNaN(Date.parse(value.toString()))) { /* eslint-disable-line */
return true;
}
if (value) {
return `"${value}" is not a valid date.`;
}
if (options.required) {
return defaultMessage;
}
return true;
};
export const upload = (value, options = {}) => {
if (value || !options.required) return true;
return defaultMessage;
};
export const relationship = (value, options = {}) => {
if (value || !options.required) return true;
return defaultMessage;
};
export const array = (value, options = {}) => {
if (options.minRows && value < options.minRows) {
return `This field requires at least ${options.minRows} row(s).`;
}
if (options.maxRows && value > options.maxRows) {
return `This field requires no more than ${options.maxRows} row(s).`;
}
if (!value && options.required) {
return 'This field requires at least one row.';
}
return true;
};
export const select = (value, options = {}) => {
if (Array.isArray(value) && value.find((input) => !options.options.find((option) => (option === input || option.value === input)))) {
return 'This field has an invalid selection';
}
if (typeof value === 'string' && !options.options.find((option) => (option === value || option.value === value))) {
return 'This field has an invalid selection';
}
if (options.required && !value) {
return defaultMessage;
}
return true;
};
export const radio = (value, options = {}) => {
const stringValue = String(value);
if ((typeof value !== 'undefined' || !options.required) && (options.options.find((option) => String(option.value) === stringValue))) return true;
return defaultMessage;
};
export const blocks = (value, options) => {
if (options.minRows && value < options.minRows) {
return `This field requires at least ${options.minRows} row(s).`;
}
if (options.maxRows && value > options.maxRows) {
return `This field requires no more than ${options.maxRows} row(s).`;
}
if (!value && options.required) {
return 'This field requires at least one row.';
}
return true;
};
export default {
number,
text,
password,
email,
textarea,
code,
wysiwyg,
richText,
checkbox,
date,
upload,
relationship,
array,
select,
radio,
blocks,
};

View File

@@ -1,9 +1,6 @@
import GraphQL, { GraphQLObjectType, GraphQLSchema } from 'graphql';
import queryComplexity, {
simpleEstimator,
fieldExtensionsEstimator,
} from 'graphql-query-complexity';
import graphQLHTTP from 'express-graphql';
import queryComplexity, { simpleEstimator, fieldExtensionsEstimator } from 'graphql-query-complexity';
import buildObjectType from './schema/buildObjectType';
import buildMutationInputType from './schema/buildMutationInputType';
import errorHandler from './errorHandler';

View File

@@ -136,7 +136,7 @@ class Payload {
// Enable static routes for all collections permitting upload
this.initStatic();
this.errorHandler = errorHandler(this.config);
this.errorHandler = errorHandler(this);
this.router.use(this.errorHandler);
this.authenticate = authenticate(this.config);

View File

@@ -3,7 +3,6 @@
import path from 'path';
import findConfig from './findConfig';
const configPath = findConfig();
const getConfig = () => {
// eslint-disable-next-line @typescript-eslint/no-var-requires