From 8809bcb5731fa28aa643fc0056fd27db06caa468 Mon Sep 17 00:00:00 2001 From: James Date: Mon, 18 May 2020 13:07:32 -0400 Subject: [PATCH] removes reliance on useAsTitle --- demo/collections/User.js | 10 ----- demo/payload.config.js | 37 +------------------ .../forms/field-types/Relationship/index.js | 4 +- .../components/views/ForgotPassword/index.js | 12 ++++-- .../views/collections/Edit/index.js | 4 +- src/errors/MissingUseAsTitle.js | 9 ----- src/errors/index.js | 2 - src/tests/globalSetup.js | 5 +-- src/users/graphql/init.js | 9 ++--- src/users/graphql/resolvers/login.js | 3 +- src/users/init.js | 2 +- src/users/operations/forgotPassword.js | 8 ++-- src/users/operations/login.js | 6 +-- src/users/operations/resetPassword.js | 3 +- src/users/users.spec.js | 15 ++++---- 15 files changed, 34 insertions(+), 95 deletions(-) delete mode 100644 src/errors/MissingUseAsTitle.js diff --git a/demo/collections/User.js b/demo/collections/User.js index 3dabdabdd9..a19eddb9d2 100644 --- a/demo/collections/User.js +++ b/demo/collections/User.js @@ -21,20 +21,10 @@ module.exports = { delete: ({ req: { user } }) => checkRole(['admin', 'user'], user), }, auth: { - passwordIndex: 1, - useAsUsername: 'email', tokenExpiration: 7200, secretKey: 'SECRET_KEY', }, fields: [ - { - name: 'email', - label: 'Email Address', - type: 'email', - unique: true, - maxLength: 100, - required: true, - }, { name: 'roles', label: 'Role', diff --git a/demo/payload.config.js b/demo/payload.config.js index 6469bcdadf..14cfffe891 100644 --- a/demo/payload.config.js +++ b/demo/payload.config.js @@ -22,8 +22,8 @@ module.exports = { Layout, File, Media, + User, ], - User, globals: [Header, Footer], port: 3000, serverURL: 'http://localhost:3000', @@ -47,41 +47,6 @@ module.exports = { defaultLocale: 'en', fallback: true, }, - uploads: { - image: { - imageSizes: [ - { - name: 'tablet', - width: 640, - height: 480, - crop: 'left top', // would it make sense for this to be set by the uploader? - }, - { - name: 'mobile', - width: 320, - height: 240, - crop: 'left top', - }, - { // Is the icon size required for the admin dashboard to work? - name: 'icon', - width: 16, - height: 16, - }, - ], - }, - profile: { - imageSizes: [ - { - name: 'full', - width: 640, - height: 480, - crop: 'center', - }, - ], - }, - }, - staticURL: '/uploads', - staticDir: 'demo/upload', productionGraphQLPlayground: false, email: { provider: 'mock', diff --git a/src/client/components/forms/field-types/Relationship/index.js b/src/client/components/forms/field-types/Relationship/index.js index 271ea0cef3..162c442d72 100644 --- a/src/client/components/forms/field-types/Relationship/index.js +++ b/src/client/components/forms/field-types/Relationship/index.js @@ -129,7 +129,7 @@ class Relationship extends Component { options: [ ...options, ...data.docs.map(doc => ({ - label: doc[collection.useAsTitle], + label: doc[collection.useAsTitle || 'id'], value: doc.id, })), ], @@ -140,7 +140,7 @@ class Relationship extends Component { const newOptions = data.docs.map((doc) => { return { - label: doc[collection.useAsTitle], + label: doc[collection.useAsTitle || doc.id], value: { relationTo: collection.slug, value: doc.id, diff --git a/src/client/components/views/ForgotPassword/index.js b/src/client/components/views/ForgotPassword/index.js index 7ece984c52..6e110de394 100644 --- a/src/client/components/views/ForgotPassword/index.js +++ b/src/client/components/views/ForgotPassword/index.js @@ -12,7 +12,13 @@ import './index.scss'; const baseClass = 'forgot-password'; -const { serverURL, routes: { admin, api } } = PAYLOAD_CONFIG; +const { + serverURL, + routes: { + admin, + api, + }, +} = PAYLOAD_CONFIG; const ForgotPassword = () => { const { addStatus } = useStatusList(); @@ -38,7 +44,7 @@ const ForgotPassword = () => {

To change your password, go to your {' '} - account + account {' '} and edit your password there.

@@ -83,7 +89,7 @@ const ForgotPassword = () => { action={`${serverURL}${api}/forgot-password`} >

Forgot Password

-

Please enter your username or email address. You will receive an email message with instructions on how to reset your password.

+

Please enter your username below. You will receive an email message with instructions on how to reset your password.

{ if (isEditing) { nav.push({ - label: data ? data[useAsTitle] : '', + label: data ? data[useAsTitle || 'id'] : '', }); } else { nav.push({ @@ -77,7 +77,7 @@ const EditView = (props) => { Edit {' '} {Object.keys(data).length > 0 - && (data[useAsTitle] ? data[useAsTitle] : '[Untitled]') + && (data[useAsTitle || 'id'] ? data[useAsTitle || 'id'] : '[Untitled]') } )} diff --git a/src/errors/MissingUseAsTitle.js b/src/errors/MissingUseAsTitle.js deleted file mode 100644 index ba2db0ba5b..0000000000 --- a/src/errors/MissingUseAsTitle.js +++ /dev/null @@ -1,9 +0,0 @@ -const APIError = require('./APIError'); - -class MissingUseAsTitle extends APIError { - constructor(collection) { - super(`${collection.labels.singular} collection is missing a useAsTitle property.`); - } -} - -module.exports = MissingUseAsTitle; diff --git a/src/errors/index.js b/src/errors/index.js index 1fdd565847..b4eaf0e6b6 100644 --- a/src/errors/index.js +++ b/src/errors/index.js @@ -4,7 +4,6 @@ const DuplicateCollection = require('./DuplicateCollection'); const DuplicateGlobal = require('./DuplicateGlobal'); const MissingCollectionLabel = require('./MissingCollectionLabel'); const MissingGlobalLabel = require('./MissingGlobalLabel'); -const MissingUseAsTitle = require('./MissingUseAsTitle'); const NotFound = require('./NotFound'); const Forbidden = require('./Forbidden'); const ValidationError = require('./ValidationError'); @@ -17,7 +16,6 @@ module.exports = { DuplicateGlobal, MissingCollectionLabel, MissingGlobalLabel, - MissingUseAsTitle, NotFound, Forbidden, ValidationError, diff --git a/src/tests/globalSetup.js b/src/tests/globalSetup.js index 8cebe1ce4c..c9040ba41b 100644 --- a/src/tests/globalSetup.js +++ b/src/tests/globalSetup.js @@ -1,17 +1,16 @@ require('isomorphic-fetch'); const server = require('../../demo/server'); const config = require('../../demo/payload.config'); -const { email, password } = require('./credentials'); +const { username, password } = require('./credentials'); const url = config.serverURL; -const usernameField = config.User.auth.useAsUsername; const globalSetup = async () => { global.PAYLOAD_SERVER = server.start(); const response = await fetch(`${url}/api/first-register`, { body: JSON.stringify({ - [usernameField]: email, + username, password, roles: ['admin', 'user'], }), diff --git a/src/users/graphql/init.js b/src/users/graphql/init.js index 0d52cb154d..ef66bce352 100644 --- a/src/users/graphql/init.js +++ b/src/users/graphql/init.js @@ -24,9 +24,6 @@ function registerUser() { plural, }, fields, - auth: { - useAsUsername, - }, }, } = this.User; @@ -89,7 +86,7 @@ function registerUser() { return jwtFields; }, [ { - name: this.User.config.auth.useAsUsername, + name: 'username', type: 'text', required: true, }, @@ -154,7 +151,7 @@ function registerUser() { this.Mutation.fields.login = { type: GraphQLString, args: { - [useAsUsername]: { type: GraphQLString }, + username: { type: GraphQLString }, password: { type: GraphQLString }, }, resolve: login(this.User), @@ -171,7 +168,7 @@ function registerUser() { this.Mutation.fields.forgotPassword = { type: new GraphQLNonNull(GraphQLBoolean), args: { - [useAsUsername]: { type: new GraphQLNonNull(GraphQLString) }, + username: { type: new GraphQLNonNull(GraphQLString) }, }, resolve: forgotPassword(this.config, this.User.Model, this.sendEmail), }; diff --git a/src/users/graphql/resolvers/login.js b/src/users/graphql/resolvers/login.js index 137dcd77c7..d1e36ce1b9 100644 --- a/src/users/graphql/resolvers/login.js +++ b/src/users/graphql/resolvers/login.js @@ -2,12 +2,11 @@ const { login } = require('../../operations'); const loginResolver = ({ Model, config }) => async (_, args, context) => { - const usernameField = config.auth.useAsUsername; const options = { Model, config, data: { - [usernameField]: args[usernameField], + username: args.username, password: args.password, }, req: context, diff --git a/src/users/init.js b/src/users/init.js index 1c25542cb8..27cb93f8e2 100644 --- a/src/users/init.js +++ b/src/users/init.js @@ -14,7 +14,7 @@ function initUser() { this.config.User.fields.push(...baseUserFields); this.config.User = sanitize(this.config.User); const userSchema = buildCollectionSchema(this.config.User, this.config); - userSchema.plugin(passportLocalMongoose, { usernameField: this.config.User.auth.useAsUsername }); + userSchema.plugin(passportLocalMongoose); this.User = { config: this.config.User, diff --git a/src/users/operations/forgotPassword.js b/src/users/operations/forgotPassword.js index 983a040fc5..2e48a41ae0 100644 --- a/src/users/operations/forgotPassword.js +++ b/src/users/operations/forgotPassword.js @@ -3,9 +3,7 @@ const { APIError } = require('../../errors'); const forgotPassword = async (args) => { try { - const usernameField = args.config.User.auth.useAsUsername; - - if (!Object.prototype.hasOwnProperty.call(args.data, usernameField)) { + if (!Object.prototype.hasOwnProperty.call(args.data, 'username')) { throw new APIError('Missing username.'); } @@ -35,7 +33,7 @@ const forgotPassword = async (args) => { let token = await crypto.randomBytes(20); token = token.toString('hex'); - const user = await Model.findOne({ [usernameField]: data[usernameField] }); + const user = await Model.findOne({ username: data.username }); if (!user) return; @@ -53,7 +51,7 @@ const forgotPassword = async (args) => { email({ from: `"${config.email.fromName}" <${config.email.fromAddress}>`, - to: data[usernameField], + to: data.username, subject: 'Password Reset', html, }); diff --git a/src/users/operations/login.js b/src/users/operations/login.js index 41b85e6042..cf19c89426 100644 --- a/src/users/operations/login.js +++ b/src/users/operations/login.js @@ -27,9 +27,7 @@ const login = async (args) => { data, } = options; - const usernameField = config.auth.useAsUsername; - const username = data[usernameField]; - const { password } = data; + const { username, password } = data; const user = await Model.findByUsername(username); @@ -50,7 +48,7 @@ const login = async (args) => { } return signedFields; }, { - [usernameField]: username, + username, }); const token = jwt.sign( diff --git a/src/users/operations/resetPassword.js b/src/users/operations/resetPassword.js index 3cbe6125c2..371a37db55 100644 --- a/src/users/operations/resetPassword.js +++ b/src/users/operations/resetPassword.js @@ -30,8 +30,7 @@ const resetPassword = async (args) => { data, } = options; - const usernameField = config.auth.useAsUsername; - const username = data[usernameField]; + const { username } = data; const user = await Model.findOne({ resetPasswordToken: data.token, diff --git a/src/users/users.spec.js b/src/users/users.spec.js index 97ee9373b9..8adc0dacdb 100644 --- a/src/users/users.spec.js +++ b/src/users/users.spec.js @@ -1,6 +1,6 @@ require('isomorphic-fetch'); const faker = require('faker'); -const { email, password } = require('../tests/credentials'); +const { username, password } = require('../tests/credentials'); /** * @jest-environment node @@ -10,7 +10,6 @@ const config = require('../../demo/payload.config'); const { payload } = require('../../demo/server'); const url = config.serverURL; -const usernameField = config.User.auth.useAsUsername; let token = null; @@ -18,7 +17,7 @@ describe('Users REST API', () => { it('should prevent registering a first user', async () => { const response = await fetch(`${url}/api/first-register`, { body: JSON.stringify({ - [usernameField]: 'thisuser@shouldbeprevented.com', + username: 'thisuser@shouldbeprevented.com', password: 'get-out', }), headers: { @@ -33,7 +32,7 @@ describe('Users REST API', () => { it('should login a user successfully', async () => { const response = await fetch(`${url}/api/login`, { body: JSON.stringify({ - [usernameField]: email, + username, password, }), headers: { @@ -60,7 +59,7 @@ describe('Users REST API', () => { const data = await response.json(); expect(response.status).toBe(200); - expect(data[usernameField]).not.toBeNull(); + expect(data.username).not.toBeNull(); }); it('should refresh a token and reset its expiration', async () => { @@ -85,7 +84,7 @@ describe('Users REST API', () => { const response = await fetch(`${url}/api/forgot-password`, { method: 'post', body: JSON.stringify({ - [usernameField]: email, + username, }), headers: { 'Content-Type': 'application/json', @@ -101,7 +100,7 @@ describe('Users REST API', () => { it('should allow a user to be created', async () => { const response = await fetch(`${url}/api/users/register`, { body: JSON.stringify({ - [usernameField]: `${faker.name.firstName()}@test.com`, + username: `${faker.name.firstName()}@test.com`, password, roles: ['editor'], }), @@ -115,7 +114,7 @@ describe('Users REST API', () => { const data = await response.json(); expect(response.status).toBe(201); - expect(data).toHaveProperty(usernameField); + expect(data).toHaveProperty('username'); expect(data).toHaveProperty('roles'); expect(data).toHaveProperty('createdAt'); });