From b1a5de9cc045f975b49bb4bfef37544b51dfd5e3 Mon Sep 17 00:00:00 2001 From: Tobias Bieniek Date: Fri, 11 Nov 2022 12:07:40 +0100 Subject: [PATCH] Implement experimental `adapterAction()` function (#37) --- addon/index.js | 21 ++++++++++++ tests/unit/adapter-actions-test.js | 51 ++++++++++++++++++++++++++++++ 2 files changed, 72 insertions(+) create mode 100644 tests/unit/adapter-actions-test.js diff --git a/addon/index.js b/addon/index.js index 9dfdd78c..8ed00fe6 100644 --- a/addon/index.js +++ b/addon/index.js @@ -34,3 +34,24 @@ export async function apiAction( return await adapter.ajax(url, method, { data }); } + +/** @experimental */ +export async function adapterAction( + adapter, + modelName, + { requestType = 'createRecord', method, path, data } +) { + assert(`Missing \`method\` option`, method); + assert( + [ + `Invalid \`method\` option: ${method}`, + `Valid options: ${VALID_METHODS.join(', ')}`, + ].join('\n'), + VALID_METHODS.includes(method) + ); + + let baseUrl = adapter.buildURL(modelName, null, null, requestType); + let url = path ? `${baseUrl}/${path}` : baseUrl; + + return await adapter.ajax(url, method, { data }); +} diff --git a/tests/unit/adapter-actions-test.js b/tests/unit/adapter-actions-test.js new file mode 100644 index 00000000..2fb7da62 --- /dev/null +++ b/tests/unit/adapter-actions-test.js @@ -0,0 +1,51 @@ +import { module, test } from 'qunit'; +import { setupTest } from 'ember-qunit'; +import { adapterAction } from '@mainmatter/ember-api-actions'; +import { ServerError } from '@ember-data/adapter/error'; + +module('adapterAction()', function (hooks) { + setupTest(hooks); + + async function prepare(context) { + let { worker, rest } = window.msw; + + worker.use( + rest.post('/users/validate-email', (req, res, ctx) => { + return res(ctx.json({ email: 'valid' })); + }) + ); + + let store = context.owner.lookup('service:store'); + let adapter = store.adapterFor('user'); + + return { worker, rest, adapter }; + } + + test('it works', async function (assert) { + let { adapter } = await prepare(this); + + let response = await adapterAction(adapter, 'user', { + method: 'POST', + path: 'validate-email', + }); + assert.deepEqual(response, { email: 'valid' }); + }); + + test('it fails as expected', async function (assert) { + let { worker, rest, adapter } = await prepare(this); + + worker.use( + rest.post('/users/validate-email', (req, res, ctx) => { + return res(ctx.status(500)); + }) + ); + + await assert.rejects( + adapterAction(adapter, 'user', { + method: 'POST', + path: 'validate-email', + }), + ServerError + ); + }); +});