insomnia/packages/insomnia-app/app/ui/redux/selectors.js
Gregory Schier 3883dc6feb
POC for Unit Test UI (#2315)
* Start working on insomnia-testing package to generate Mocha code

* Moved some things around

* Integration tests and ability to run multiple files

* Fix integration tests

* Rename runSuite to runMochaTests

* Add types for test results

* Fix lint errors

* Play with Chia assertions

* insomnia and chai globals, plus a bunch of improvements

* Stub chai and axios Flow types

* Ability to reference requests by ID

* Fix chai flow-typed location

* Address PR comments (small tweaks)

* Basic UI going

* Lots and lots and lots

* Pretty-much done with the unit test UI

* Minor CSS tweak

* Activity bar triple toggle and more

* Minor tweak

* Unit Test and Suite deletion

* Bump Designer version

* Fix eslint stuff

* Fix insomnia-testing tests

* Fix tests

* lib@2.2.9

* Remove tests tab from response pane

* Hook up Insomnia networking

* Fix linting

* Bump version for alpha

* Remove extra ActivityToggleSwitch

* Remove unused import

* Add test:pre-release script that excludes CLI tests

* Less repetition

* Clean some things up

* Tweaks after self-cr

* Undo request ID tag

* Swap out switch for new activity toggle component

* Extra check

* Remove dead code

* Delete dead test

* Oops, revert example code

* PR feedback

* More PR comment addresses
2020-07-01 14:17:14 -07:00

391 lines
11 KiB
JavaScript

import { createSelector } from 'reselect';
import { fuzzyMatchAll } from '../../common/misc';
import * as models from '../../models';
// ~~~~~~~~~ //
// Selectors //
// ~~~~~~~~~ //
export const selectEntitiesLists = createSelector(
state => state.entities,
entities => {
const entitiesLists = {};
for (const k of Object.keys(entities)) {
const entityMap = entities[k];
entitiesLists[k] = Object.keys(entityMap).map(id => entityMap[id]);
}
return entitiesLists;
},
);
export const selectEntitiesChildrenMap = createSelector(selectEntitiesLists, entities => {
const parentLookupMap = {};
for (const k of Object.keys(entities)) {
for (const e of entities[k]) {
if (!e.parentId) {
continue;
}
if (parentLookupMap[e.parentId]) {
parentLookupMap[e.parentId].push(e);
} else {
parentLookupMap[e.parentId] = [e];
}
}
}
return parentLookupMap;
});
export const selectSettings = createSelector(selectEntitiesLists, entities => {
return entities.settings[0] || models.settings.init();
});
export const selectActiveWorkspace = createSelector(
state => selectEntitiesLists(state).workspaces,
state => state.entities,
state => state.global.activeWorkspaceId,
(workspaces, entities, activeWorkspaceId) => {
return entities.workspaces[activeWorkspaceId] || workspaces[0];
},
);
export const selectActiveWorkspaceMeta = createSelector(
selectActiveWorkspace,
selectEntitiesLists,
(activeWorkspace, entities) => {
const id = activeWorkspace ? activeWorkspace._id : 'n/a';
return entities.workspaceMetas.find(m => m.parentId === id);
},
);
export const selectActiveEnvironment = createSelector(
selectActiveWorkspaceMeta,
selectEntitiesLists,
(meta, entities) => {
if (!meta) {
return null;
}
return entities.environments.find(e => e._id === meta.activeEnvironmentId) || null;
},
);
export const selectActiveWorkspaceClientCertificates = createSelector(
selectEntitiesLists,
selectActiveWorkspace,
(entities, activeWorkspace) => {
return entities.clientCertificates.filter(c => c.parentId === activeWorkspace._id);
},
);
export const selectActiveGitRepository = createSelector(
selectEntitiesLists,
selectActiveWorkspaceMeta,
(entities, activeWorkspaceMeta) => {
if (!activeWorkspaceMeta) {
return null;
}
const id = activeWorkspaceMeta ? activeWorkspaceMeta.gitRepositoryId : 'n/a';
const repo = entities.gitRepositories.find(r => r._id === id);
return repo || null;
},
);
export const selectCollapsedRequestGroups = createSelector(selectEntitiesLists, entities => {
const collapsed = {};
// Default all to collapsed
for (const requestGroup of entities.requestGroups) {
collapsed[requestGroup._id] = true;
}
// Update those that have metadata (not all do)
for (const meta of entities.requestGroupMetas) {
collapsed[meta.parentId] = meta.collapsed;
}
return collapsed;
});
export const selectActiveWorkspaceEntities = createSelector(
selectActiveWorkspace,
selectEntitiesChildrenMap,
(activeWorkspace, childrenMap) => {
const descendants = [activeWorkspace];
const addChildrenOf = parent => {
// Don't add children of requests (eg. auth requests)
if (parent.type === models.request.type) {
return [];
}
const children = childrenMap[parent._id] || [];
for (const child of children) {
descendants.push(child);
addChildrenOf(child);
}
};
// Kick off the recursion
addChildrenOf(activeWorkspace);
return descendants;
},
);
export const selectPinnedRequests = createSelector(selectEntitiesLists, entities => {
const pinned = {};
// Default all to unpinned
for (const request of entities.requests) {
pinned[request._id] = false;
}
// Update those that have metadata (not all do)
for (const meta of entities.requestMetas) {
pinned[meta.parentId] = meta.pinned;
}
return pinned;
});
export const selectSidebarChildren = createSelector(
selectCollapsedRequestGroups,
selectPinnedRequests,
selectActiveWorkspace,
selectActiveWorkspaceMeta,
selectEntitiesChildrenMap,
(collapsed, pinned, activeWorkspace, activeWorkspaceMeta, childrenMap) => {
const sidebarFilter = activeWorkspaceMeta ? activeWorkspaceMeta.sidebarFilter : '';
function next(parentId, pinnedChildren) {
const children = (childrenMap[parentId] || [])
.filter(doc => {
return doc.type === models.request.type || doc.type === models.requestGroup.type;
})
.sort((a, b) => {
if (a.metaSortKey === b.metaSortKey) {
return a._id > b._id ? -1 : 1;
} else {
return a.metaSortKey < b.metaSortKey ? -1 : 1;
}
});
if (children.length > 0) {
return children.map(c => {
const child = {
doc: c,
hidden: false,
collapsed: !!collapsed[c._id],
pinned: !!pinned[c._id],
};
if (child.pinned) {
pinnedChildren.push(child);
}
// Don't add children of requests
child.children = c.type === models.request.type ? [] : next(c._id, pinnedChildren);
return child;
});
} else {
return children;
}
}
function matchChildren(children, parentNames = []) {
// Bail early if no filter defined
if (!sidebarFilter) {
return children;
}
for (const child of children) {
// Gather all parents so we can match them too
matchChildren(child.children, [...parentNames, child.doc.name]);
const hasMatchedChildren = child.children.find(c => c.hidden === false);
// Try to match request attributes
const { name, method } = child.doc;
const match = fuzzyMatchAll(sidebarFilter, [name, method, ...parentNames], {
splitSpace: true,
});
// Update hidden state depending on whether it matched
const matched = hasMatchedChildren || match;
child.hidden = !matched;
}
return children;
}
const pinnedChildren = [];
const childrenTree = next(activeWorkspace._id, pinnedChildren);
const matchedChildren = matchChildren(childrenTree);
return { pinned: pinnedChildren, all: matchedChildren };
},
);
export const selectWorkspaceRequestsAndRequestGroups = createSelector(
selectActiveWorkspaceEntities,
entities => {
return entities.filter(
e => e.type === models.request.type || e.type === models.requestGroup.type,
);
},
);
export const selectActiveRequest = createSelector(
state => state.entities,
selectActiveWorkspaceMeta,
(entities, workspaceMeta) => {
const id = workspaceMeta ? workspaceMeta.activeRequestId : 'n/a';
return entities.requests[id] || null;
},
);
export const selectActiveCookieJar = createSelector(
selectEntitiesLists,
selectActiveWorkspace,
(entities, workspace) => {
const cookieJar = entities.cookieJars.find(cj => cj.parentId === workspace._id);
return cookieJar || null;
},
);
export const selectActiveOAuth2Token = createSelector(
selectEntitiesLists,
selectActiveWorkspaceMeta,
(entities, workspaceMeta) => {
const id = workspaceMeta ? workspaceMeta.activeRequestId : 'n/a';
return entities.oAuth2Tokens.find(t => t.parentId === id);
},
);
export const selectUnseenWorkspaces = createSelector(selectEntitiesLists, entities => {
const { workspaces, workspaceMetas } = entities;
return workspaces.filter(workspace => {
const meta = workspaceMetas.find(m => m.parentId === workspace._id);
return !!(meta && !meta.hasSeen);
});
});
export const selectActiveRequestMeta = createSelector(
selectActiveRequest,
selectEntitiesLists,
(activeRequest, entities) => {
const id = activeRequest ? activeRequest._id : 'n/a';
return entities.requestMetas.find(m => m.parentId === id);
},
);
export const selectActiveRequestResponses = createSelector(
selectActiveRequest,
selectEntitiesLists,
selectActiveEnvironment,
selectSettings,
(activeRequest, entities, activeEnvironment, settings) => {
const requestId = activeRequest ? activeRequest._id : 'n/a';
// Filter responses down if the setting is enabled
return entities.responses
.filter(response => {
const requestMatches = requestId === response.parentId;
if (settings.filterResponsesByEnv) {
const activeEnvironmentId = activeEnvironment ? activeEnvironment._id : null;
const environmentMatches = response.environmentId === activeEnvironmentId;
return requestMatches && environmentMatches;
} else {
return requestMatches;
}
})
.sort((a, b) => (a.created > b.created ? -1 : 1));
},
);
export const selectActiveResponse = createSelector(
selectActiveRequestMeta,
selectActiveRequestResponses,
(activeRequestMeta, responses) => {
const activeResponseId = activeRequestMeta ? activeRequestMeta.activeResponseId : 'n/a';
const activeResponse = responses.find(response => response._id === activeResponseId);
if (activeResponse) {
return activeResponse;
}
return responses[0] || null;
},
);
export const selectActiveUnitTestResult = createSelector(
selectEntitiesLists,
selectActiveWorkspace,
(entities, activeWorkspace) => {
let recentResult = null;
for (const r of entities.unitTestResults) {
if (r.parentId !== activeWorkspace._id) {
continue;
}
if (!recentResult) {
recentResult = r;
continue;
}
if (r.created > recentResult.created) {
recentResult = r;
}
}
return recentResult;
},
);
export const selectActiveUnitTestSuite = createSelector(
selectEntitiesLists,
selectActiveWorkspaceMeta,
(entities, activeWorkspaceMeta) => {
if (!activeWorkspaceMeta) {
return null;
}
const id = activeWorkspaceMeta.activeUnitTestSuiteId;
return entities.unitTestSuites.find(s => s._id === id) || null;
},
);
export const selectActiveUnitTests = createSelector(
selectEntitiesLists,
selectActiveUnitTestSuite,
(entities, activeUnitTestSuite) => {
if (!activeUnitTestSuite) {
return [];
}
return entities.unitTests.filter(s => s.parentId === activeUnitTestSuite._id);
},
);
export const selectActiveUnitTestSuites = createSelector(
selectEntitiesLists,
selectActiveWorkspace,
(entities, activeWorkspace) => {
return entities.unitTestSuites.filter(s => s.parentId === activeWorkspace._id);
},
);
export const selectSyncItems = createSelector(selectActiveWorkspaceEntities, workspaceEntities =>
workspaceEntities.filter(models.canSync).map(doc => ({
key: doc._id,
name: doc.name || '',
document: doc,
})),
);