refactor(web): remove typescript
This commit is contained in:
@@ -1,16 +1,12 @@
|
||||
import type { IAuthenticationStep, IJSONObject } from 'types';
|
||||
import apolloClient from 'graphql/client';
|
||||
import MUTATIONS from 'graphql/mutations';
|
||||
var AuthenticationSteps;
|
||||
(function (AuthenticationSteps) {
|
||||
AuthenticationSteps['Mutation'] = 'mutation';
|
||||
AuthenticationSteps['OpenWithPopup'] = 'openWithPopup';
|
||||
})(AuthenticationSteps || (AuthenticationSteps = {}));
|
||||
|
||||
enum AuthenticationSteps {
|
||||
Mutation = 'mutation',
|
||||
OpenWithPopup = 'openWithPopup',
|
||||
}
|
||||
|
||||
const processMutation = async (
|
||||
step: IAuthenticationStep,
|
||||
variables: IJSONObject
|
||||
) => {
|
||||
const processMutation = async (step, variables) => {
|
||||
const mutation = MUTATIONS[step.name];
|
||||
const mutationResponse = await apolloClient.mutate({
|
||||
mutation,
|
||||
@@ -20,78 +16,52 @@ const processMutation = async (
|
||||
},
|
||||
});
|
||||
const responseData = mutationResponse.data[step.name];
|
||||
|
||||
return responseData;
|
||||
};
|
||||
|
||||
const parseUrlSearchParams = (event: any) => {
|
||||
const parseUrlSearchParams = (event) => {
|
||||
const searchParams = new URLSearchParams(event.data.payload.search);
|
||||
const hashParams = new URLSearchParams(event.data.payload.hash.substring(1));
|
||||
|
||||
const searchParamsObject = getObjectOfEntries(searchParams.entries());
|
||||
const hashParamsObject = getObjectOfEntries(hashParams.entries());
|
||||
|
||||
return {
|
||||
...hashParamsObject,
|
||||
...searchParamsObject,
|
||||
};
|
||||
};
|
||||
|
||||
function getObjectOfEntries(iterator: any) {
|
||||
const result: any = {};
|
||||
|
||||
function getObjectOfEntries(iterator) {
|
||||
const result = {};
|
||||
for (const [key, value] of iterator) {
|
||||
result[key] = value;
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
const processOpenWithPopup = (
|
||||
step: IAuthenticationStep,
|
||||
variables: IJSONObject
|
||||
) => {
|
||||
const processOpenWithPopup = (step, variables) => {
|
||||
return new Promise((resolve, reject) => {
|
||||
const windowFeatures =
|
||||
'toolbar=no, titlebar=no, menubar=no, width=500, height=700, top=100, left=100';
|
||||
const url = variables.url;
|
||||
|
||||
const popup = window.open(
|
||||
url as string,
|
||||
'_blank',
|
||||
windowFeatures
|
||||
) as WindowProxy;
|
||||
const popup = window.open(url, '_blank', windowFeatures);
|
||||
popup?.focus();
|
||||
|
||||
const closeCheckIntervalId = setInterval(() => {
|
||||
if (!popup) return;
|
||||
|
||||
if (popup?.closed) {
|
||||
clearInterval(closeCheckIntervalId);
|
||||
reject({ message: 'Error occured while verifying credentials!' });
|
||||
}
|
||||
}, 1000);
|
||||
|
||||
const messageHandler = async (event: MessageEvent) => {
|
||||
const messageHandler = async (event) => {
|
||||
if (event.data.source !== 'automatisch') {
|
||||
return;
|
||||
}
|
||||
|
||||
const data = parseUrlSearchParams(event);
|
||||
window.removeEventListener('message', messageHandler);
|
||||
|
||||
clearInterval(closeCheckIntervalId);
|
||||
resolve(data);
|
||||
};
|
||||
|
||||
window.addEventListener('message', messageHandler, false);
|
||||
});
|
||||
};
|
||||
|
||||
export const processStep = async (
|
||||
step: IAuthenticationStep,
|
||||
variables: IJSONObject
|
||||
): Promise<any> => {
|
||||
export const processStep = async (step, variables) => {
|
||||
if (step.type === AuthenticationSteps.Mutation) {
|
||||
return processMutation(step, variables);
|
||||
} else if (step.type === AuthenticationSteps.OpenWithPopup) {
|
@@ -1,48 +1,27 @@
|
||||
import template from 'lodash/template';
|
||||
import type { IAuthenticationStepField, IJSONObject } from 'types';
|
||||
|
||||
const interpolate = /{([\s\S]+?)}/g;
|
||||
|
||||
type Variables = {
|
||||
[key: string]: any;
|
||||
};
|
||||
|
||||
type IVariable = Omit<IAuthenticationStepField, 'properties'> &
|
||||
Partial<Pick<IAuthenticationStepField, 'properties'>>;
|
||||
|
||||
const computeAuthStepVariables = (
|
||||
variableSchema: IVariable[],
|
||||
aggregatedData: IJSONObject
|
||||
): IJSONObject => {
|
||||
const variables: Variables = {};
|
||||
|
||||
const computeAuthStepVariables = (variableSchema, aggregatedData) => {
|
||||
const variables = {};
|
||||
for (const variable of variableSchema) {
|
||||
if (variable.properties) {
|
||||
variables[variable.name] = computeAuthStepVariables(
|
||||
variable.properties,
|
||||
aggregatedData
|
||||
);
|
||||
|
||||
continue;
|
||||
}
|
||||
|
||||
if (variable.value) {
|
||||
if (variable.value.endsWith('.all}')) {
|
||||
const key = variable.value.replace('{', '').replace('.all}', '');
|
||||
variables[variable.name] = aggregatedData[key];
|
||||
|
||||
continue;
|
||||
}
|
||||
|
||||
const computedVariable = template(variable.value, { interpolate })(
|
||||
aggregatedData
|
||||
);
|
||||
|
||||
variables[variable.name] = computedVariable;
|
||||
}
|
||||
}
|
||||
|
||||
return variables;
|
||||
};
|
||||
|
||||
export default computeAuthStepVariables;
|
@@ -1,20 +1,5 @@
|
||||
import { IRole, IPermission } from 'types';
|
||||
|
||||
type ComputeAction = {
|
||||
conditions: Record<string, boolean>;
|
||||
value: boolean;
|
||||
};
|
||||
type ComputedActions = Record<string, ComputeAction>;
|
||||
type ComputedPermissions = Record<string, ComputedActions>;
|
||||
export type RoleWithComputedPermissions = IRole & {
|
||||
computedPermissions: ComputedPermissions;
|
||||
};
|
||||
|
||||
export function getRoleWithComputedPermissions(
|
||||
role?: IRole
|
||||
): Partial<RoleWithComputedPermissions> {
|
||||
export function getRoleWithComputedPermissions(role) {
|
||||
if (!role) return {};
|
||||
|
||||
const computedPermissions = role.permissions.reduce(
|
||||
(computedPermissions, permission) => ({
|
||||
...computedPermissions,
|
||||
@@ -28,26 +13,21 @@ export function getRoleWithComputedPermissions(
|
||||
},
|
||||
},
|
||||
}),
|
||||
{} as ComputedPermissions
|
||||
{}
|
||||
);
|
||||
|
||||
return {
|
||||
...role,
|
||||
computedPermissions,
|
||||
};
|
||||
}
|
||||
|
||||
export function getPermissions(computedPermissions?: ComputedPermissions) {
|
||||
export function getPermissions(computedPermissions) {
|
||||
if (!computedPermissions) return [];
|
||||
|
||||
return Object.entries(computedPermissions).reduce(
|
||||
(permissions, computedPermissionEntry) => {
|
||||
const [subject, actionsWithConditions] = computedPermissionEntry;
|
||||
|
||||
for (const action in actionsWithConditions) {
|
||||
const { value: permitted, conditions = {} } =
|
||||
actionsWithConditions[action];
|
||||
|
||||
if (permitted) {
|
||||
permissions.push({
|
||||
action,
|
||||
@@ -58,9 +38,8 @@ export function getPermissions(computedPermissions?: ComputedPermissions) {
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
return permissions;
|
||||
},
|
||||
[] as Partial<IPermission>[]
|
||||
[]
|
||||
);
|
||||
}
|
@@ -1,41 +1,22 @@
|
||||
import template from 'lodash/template';
|
||||
import type { IAuthenticationStepField, IJSONObject } from 'types';
|
||||
|
||||
const interpolate = /{([\s\S]+?)}/g;
|
||||
|
||||
type Variables = {
|
||||
[key: string]: any;
|
||||
};
|
||||
|
||||
type IVariable = Omit<IAuthenticationStepField, 'properties'> &
|
||||
Partial<Pick<IAuthenticationStepField, 'properties'>>;
|
||||
|
||||
const computeAuthStepVariables = (
|
||||
variableSchema: IVariable[],
|
||||
aggregatedData: IJSONObject
|
||||
): IJSONObject => {
|
||||
const variables: Variables = {};
|
||||
|
||||
const computeAuthStepVariables = (variableSchema, aggregatedData) => {
|
||||
const variables = {};
|
||||
for (const variable of variableSchema) {
|
||||
if (variable.properties) {
|
||||
variables[variable.name] = computeAuthStepVariables(
|
||||
variable.properties,
|
||||
aggregatedData
|
||||
);
|
||||
|
||||
continue;
|
||||
}
|
||||
|
||||
if (variable.value) {
|
||||
const computedVariable = template(variable.value, { interpolate })(
|
||||
aggregatedData
|
||||
);
|
||||
|
||||
variables[variable.name] = computedVariable;
|
||||
}
|
||||
}
|
||||
|
||||
return variables;
|
||||
};
|
||||
|
||||
export default computeAuthStepVariables;
|
4
packages/web/src/helpers/copyInputValue.js
Normal file
4
packages/web/src/helpers/copyInputValue.js
Normal file
@@ -0,0 +1,4 @@
|
||||
import copy from 'clipboard-copy';
|
||||
export default function copyInputValue(element) {
|
||||
copy(element.value);
|
||||
}
|
@@ -1,5 +0,0 @@
|
||||
import copy from 'clipboard-copy';
|
||||
|
||||
export default function copyInputValue(element: HTMLInputElement): void {
|
||||
copy(element.value);
|
||||
}
|
@@ -2,52 +2,43 @@ import get from 'lodash/get';
|
||||
import set from 'lodash/set';
|
||||
import forIn from 'lodash/forIn';
|
||||
import isPlainObject from 'lodash/isPlainObject';
|
||||
|
||||
export default function filterObject(
|
||||
data: any,
|
||||
searchTerm: string,
|
||||
data,
|
||||
searchTerm,
|
||||
result = {},
|
||||
prefix: string[] = [],
|
||||
prefix = [],
|
||||
withinArray = false
|
||||
) {
|
||||
if (withinArray) {
|
||||
const containerValue = get(result, prefix, []);
|
||||
|
||||
result = filterObject(
|
||||
data,
|
||||
searchTerm,
|
||||
result,
|
||||
prefix.concat(containerValue.length.toString())
|
||||
);
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
if (isPlainObject(data)) {
|
||||
forIn(data, (value, key) => {
|
||||
const fullKey = [...prefix, key];
|
||||
|
||||
if (key.toLowerCase().includes(searchTerm)) {
|
||||
set(result, fullKey, value);
|
||||
return;
|
||||
}
|
||||
|
||||
result = filterObject(value, searchTerm, result, fullKey);
|
||||
});
|
||||
}
|
||||
|
||||
if (Array.isArray(data)) {
|
||||
forIn(data, (value) => {
|
||||
result = filterObject(value, searchTerm, result, prefix, true);
|
||||
});
|
||||
}
|
||||
|
||||
if (
|
||||
['string', 'number'].includes(typeof data) &&
|
||||
String(data).toLowerCase().includes(searchTerm)
|
||||
) {
|
||||
set(result, prefix, data);
|
||||
}
|
||||
|
||||
return result;
|
||||
};
|
||||
}
|
@@ -1,16 +1,12 @@
|
||||
import lodashIsEmpty from 'lodash/isEmpty';
|
||||
|
||||
export default function isEmpty(value: any) {
|
||||
export default function isEmpty(value) {
|
||||
if (value === undefined && value === null) return true;
|
||||
|
||||
if (Array.isArray(value) || typeof value === 'string') {
|
||||
return value.length === 0;
|
||||
}
|
||||
|
||||
if (!Number.isNaN(value)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// covers objects and anything else possibly
|
||||
return lodashIsEmpty(value);
|
||||
};
|
||||
}
|
@@ -1,18 +1,12 @@
|
||||
import { IJSONObject } from 'types';
|
||||
import set from 'lodash/set';
|
||||
|
||||
export default function nestObject<T = IJSONObject>(
|
||||
config: IJSONObject | undefined
|
||||
): Partial<T> {
|
||||
export default function nestObject(config) {
|
||||
if (!config) return {};
|
||||
const result = {};
|
||||
|
||||
for (const key in config) {
|
||||
if (Object.prototype.hasOwnProperty.call(config, key)) {
|
||||
const value = config[key];
|
||||
set(result, key, value);
|
||||
}
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
8
packages/web/src/helpers/storage.js
Normal file
8
packages/web/src/helpers/storage.js
Normal file
@@ -0,0 +1,8 @@
|
||||
const NAMESPACE = 'automatisch';
|
||||
const makeKey = (key) => `${NAMESPACE}.${key}`;
|
||||
export const setItem = (key, value) => {
|
||||
return localStorage.setItem(makeKey(key), value);
|
||||
};
|
||||
export const getItem = (key) => {
|
||||
return localStorage.getItem(makeKey(key));
|
||||
};
|
@@ -1,10 +0,0 @@
|
||||
const NAMESPACE = 'automatisch';
|
||||
const makeKey = (key: string) => `${NAMESPACE}.${key}`;
|
||||
|
||||
export const setItem = (key: string, value: string) => {
|
||||
return localStorage.setItem(makeKey(key), value);
|
||||
};
|
||||
|
||||
export const getItem = (key: string) => {
|
||||
return localStorage.getItem(makeKey(key));
|
||||
};
|
12
packages/web/src/helpers/translationValues.jsx
Normal file
12
packages/web/src/helpers/translationValues.jsx
Normal file
@@ -0,0 +1,12 @@
|
||||
import { Link as RouterLink } from 'react-router-dom';
|
||||
import Link from '@mui/material/Link';
|
||||
export const generateInternalLink = (link) => (str) => (
|
||||
<Link component={RouterLink} to={link}>
|
||||
{str}
|
||||
</Link>
|
||||
);
|
||||
export const generateExternalLink = (link) => (str) => (
|
||||
<Link href={link} target="_blank">
|
||||
{str}
|
||||
</Link>
|
||||
);
|
@@ -1,16 +0,0 @@
|
||||
import { Link as RouterLink } from 'react-router-dom';
|
||||
import Link from '@mui/material/Link';
|
||||
|
||||
export const generateInternalLink = (link: string) => (str: string) =>
|
||||
(
|
||||
<Link component={RouterLink} to={link}>
|
||||
{str}
|
||||
</Link>
|
||||
);
|
||||
|
||||
export const generateExternalLink = (link: string) => (str: string) =>
|
||||
(
|
||||
<Link href={link} target="_blank">
|
||||
{str}
|
||||
</Link>
|
||||
);
|
@@ -3,22 +3,17 @@ import {
|
||||
fieldPatternMatcher,
|
||||
mongoQueryMatcher,
|
||||
} from '@casl/ability';
|
||||
import { IUser } from 'types';
|
||||
|
||||
// Must be kept in sync with `packages/backend/src/helpers/user-ability.ts`!
|
||||
export default function userAbility(user: IUser) {
|
||||
export default function userAbility(user) {
|
||||
const permissions = user?.permissions;
|
||||
const role = user?.role;
|
||||
|
||||
// We're not using mongo, but our fields, conditions match
|
||||
const options = {
|
||||
conditionsMatcher: mongoQueryMatcher,
|
||||
fieldMatcher: fieldPatternMatcher,
|
||||
};
|
||||
|
||||
if (!role || !permissions) {
|
||||
return new PureAbility([], options);
|
||||
}
|
||||
|
||||
return new PureAbility<[string, string], string[]>(permissions, options);
|
||||
return new PureAbility(permissions, options);
|
||||
}
|
Reference in New Issue
Block a user