fix: Prevent accidental nested storages

This commit is contained in:
Joachim Van Herwegen 2022-08-24 13:28:48 +02:00
parent cf74ce3d2a
commit 4d9d1b90b0
19 changed files with 75 additions and 65 deletions

View File

@ -19,7 +19,8 @@ The `@context` needs to be updated to
The following changes pertain to the imports in the default configs: The following changes pertain to the imports in the default configs:
- ... - All default configurations which had setup disabled have been updated to also disable registration.
This is done to prevent configurations with accidental nested storage containers.
The following changes are relevant for v5 custom configs that replaced certain features. The following changes are relevant for v5 custom configs that replaced certain features.

View File

@ -3,13 +3,14 @@
"@graph": [ "@graph": [
{ {
"comment": "Handles everything related to the first-time server setup.", "comment": "Handles everything related to the first-time server setup.",
"@id": "urn:solid-server:default:SetupHttpHandler", "@id": "urn:solid-server:default:SetupParsingHandler",
"@type": "ParsingHttpHandler", "@type": "ParsingHttpHandler",
"args_requestParser": { "@id": "urn:solid-server:default:RequestParser" }, "args_requestParser": { "@id": "urn:solid-server:default:RequestParser" },
"args_metadataCollector": { "@id": "urn:solid-server:default:OperationMetadataCollector" }, "args_metadataCollector": { "@id": "urn:solid-server:default:OperationMetadataCollector" },
"args_errorHandler": { "@id": "urn:solid-server:default:ErrorHandler" }, "args_errorHandler": { "@id": "urn:solid-server:default:ErrorHandler" },
"args_responseWriter": { "@id": "urn:solid-server:default:ResponseWriter" }, "args_responseWriter": { "@id": "urn:solid-server:default:ResponseWriter" },
"args_operationHandler": { "args_operationHandler": {
"@id": "urn:solid-server:default:SetupHttpHandler",
"@type": "SetupHttpHandler", "@type": "SetupHttpHandler",
"args_handler": { "args_handler": {
"@type": "SetupHandler", "@type": "SetupHandler",

View File

@ -17,7 +17,7 @@
"args_targetExtractor": { "@id": "urn:solid-server:default:TargetExtractor" }, "args_targetExtractor": { "@id": "urn:solid-server:default:TargetExtractor" },
"args_allowedMethods": [ "*" ], "args_allowedMethods": [ "*" ],
"args_allowedPathNames": [ "/setup" ], "args_allowedPathNames": [ "/setup" ],
"args_handler": { "@id": "urn:solid-server:default:SetupHttpHandler" } "args_handler": { "@id": "urn:solid-server:default:SetupParsingHandler" }
} }
} }
] ]

View File

@ -22,7 +22,7 @@
"args_targetExtractor": { "@id": "urn:solid-server:default:TargetExtractor" }, "args_targetExtractor": { "@id": "urn:solid-server:default:TargetExtractor" },
"args_allowedMethods": [ "*" ], "args_allowedMethods": [ "*" ],
"args_allowedPathNames": [ "/setup" ], "args_allowedPathNames": [ "/setup" ],
"args_handler": { "@id": "urn:solid-server:default:SetupHttpHandler" } "args_handler": { "@id": "urn:solid-server:default:SetupParsingHandler" }
} }
] ]
} }

View File

@ -34,7 +34,7 @@
], ],
"@graph": [ "@graph": [
{ {
"comment": "A single-pod server that stores its resources in memory." "comment": "A Solid server that stores its resources in memory."
} }
] ]
} }

View File

@ -14,7 +14,7 @@
"css:config/identity/handler/default.json", "css:config/identity/handler/default.json",
"css:config/identity/ownership/token.json", "css:config/identity/ownership/token.json",
"css:config/identity/pod/static.json", "css:config/identity/pod/static.json",
"css:config/identity/registration/enabled.json", "css:config/identity/registration/disabled.json",
"css:config/ldp/authentication/dpop-bearer.json", "css:config/ldp/authentication/dpop-bearer.json",
"css:config/ldp/authorization/webacl.json", "css:config/ldp/authorization/webacl.json",
"css:config/ldp/handler/default.json", "css:config/ldp/handler/default.json",

View File

@ -34,7 +34,7 @@
], ],
"@graph": [ "@graph": [
{ {
"comment": "A single-pod server that stores its resources on disk." "comment": "A Solid server that stores its resources on disk."
} }
] ]
} }

View File

@ -30,6 +30,12 @@
"HtmlViewHandler:_templates_value": { "@id": "urn:solid-server:auth:password:RegistrationRoute" } "HtmlViewHandler:_templates_value": { "@id": "urn:solid-server:auth:password:RegistrationRoute" }
} }
] ]
},
{
"comment": "Root access is disabled when registration is enabled to prevent nested storage containers.",
"@id": "urn:solid-server:default:SetupHttpHandler",
"@type": "SetupHttpHandler",
"allowRootPod": false
} }
] ]
} }

View File

@ -34,7 +34,7 @@
], ],
"@graph": [ "@graph": [
{ {
"comment": "A single-pod server that stores its resources in memory with support for subdomain identifiers." "comment": "A Solid server that stores its resources in memory with support for subdomain identifiers."
} }
] ]
} }

View File

@ -14,7 +14,7 @@
"css:config/identity/handler/default.json", "css:config/identity/handler/default.json",
"css:config/identity/ownership/token.json", "css:config/identity/ownership/token.json",
"css:config/identity/pod/static.json", "css:config/identity/pod/static.json",
"css:config/identity/registration/enabled.json", "css:config/identity/registration/disabled.json",
"css:config/ldp/authentication/dpop-bearer.json", "css:config/ldp/authentication/dpop-bearer.json",
"css:config/ldp/authorization/webacl.json", "css:config/ldp/authorization/webacl.json",
"css:config/ldp/handler/default.json", "css:config/ldp/handler/default.json",

View File

@ -14,7 +14,7 @@
"css:config/identity/handler/default.json", "css:config/identity/handler/default.json",
"css:config/identity/ownership/token.json", "css:config/identity/ownership/token.json",
"css:config/identity/pod/static.json", "css:config/identity/pod/static.json",
"css:config/identity/registration/enabled.json", "css:config/identity/registration/disabled.json",
"css:config/ldp/authentication/dpop-bearer.json", "css:config/ldp/authentication/dpop-bearer.json",
"css:config/ldp/authorization/webacl.json", "css:config/ldp/authorization/webacl.json",
"css:config/ldp/handler/default.json", "css:config/ldp/handler/default.json",

View File

@ -35,7 +35,7 @@
"@graph": [ "@graph": [
{ {
"comment": [ "comment": [
"A single-pod server that stores its resources in a SPARQL endpoint.", "A Solid server that stores its resources in a SPARQL endpoint.",
"This server only supports RDF data. For this reason it can not use its resource store for internal key/value storage." "This server only supports RDF data. For this reason it can not use its resource store for internal key/value storage."
] ]
} }

View File

@ -13,7 +13,7 @@ The links here assume the server is hosted at `http://localhost:3000/`.
## Registering an account ## Registering an account
To register an account, you can go to `http://localhost:3000/idp/register/` if this feature is enabled, To register an account, you can go to `http://localhost:3000/idp/register/` if this feature is enabled,
which it is on all configurations we provide. which it is on most configurations we provide.
Currently our registration page ties 3 features together on the same page: Currently our registration page ties 3 features together on the same page:
* Creating an account on the server. * Creating an account on the server.

View File

@ -110,12 +110,12 @@ export class RegistrationManager {
* * Only create a root pod when allowed. * * Only create a root pod when allowed.
* *
* @param input - Input parameters for the registration procedure. * @param input - Input parameters for the registration procedure.
* @param allowRoot - If creating a pod in the root container should be allowed. * @param allowRootPod - If creating a pod in the root container should be allowed.
* *
* @returns A cleaned up version of the input parameters. * @returns A cleaned up version of the input parameters.
* Only (trimmed) parameters that are relevant to the registration procedure will be retained. * Only (trimmed) parameters that are relevant to the registration procedure will be retained.
*/ */
public validateInput(input: NodeJS.Dict<unknown>, allowRoot = false): RegistrationParams { public validateInput(input: NodeJS.Dict<unknown>, allowRootPod: boolean): RegistrationParams {
const { const {
email, password, confirmPassword, webId, podName, register, createPod, createWebId, template, rootPod, email, password, confirmPassword, webId, podName, register, createPod, createWebId, template, rootPod,
} = input; } = input;
@ -135,7 +135,7 @@ export class RegistrationManager {
rootPod: Boolean(rootPod), rootPod: Boolean(rootPod),
}; };
assert(validated.register || validated.createPod, 'Please register for a WebID or create a Pod.'); assert(validated.register || validated.createPod, 'Please register for a WebID or create a Pod.');
assert(allowRoot || !validated.rootPod, 'Creating a root pod is not supported.'); assert(allowRootPod || !validated.rootPod, 'Creating a root pod is not supported.');
// Parse WebID // Parse WebID
if (!validated.createWebId) { if (!validated.createWebId) {
@ -171,7 +171,7 @@ export class RegistrationManager {
* * Ownership will be verified when the WebID is provided. * * Ownership will be verified when the WebID is provided.
* * When registering and creating a pod, the base URL will be used as oidcIssuer value. * * When registering and creating a pod, the base URL will be used as oidcIssuer value.
*/ */
public async register(input: RegistrationParams, allowRoot = false): Promise<RegistrationResponse> { public async register(input: RegistrationParams, allowRootPod: boolean): Promise<RegistrationResponse> {
// This is only used when createWebId and/or createPod are true // This is only used when createWebId and/or createPod are true
let podBaseUrl: ResourceIdentifier | undefined; let podBaseUrl: ResourceIdentifier | undefined;
if (input.createPod) { if (input.createPod) {
@ -213,7 +213,7 @@ export class RegistrationManager {
try { try {
// Only allow overwrite for root pods // Only allow overwrite for root pods
await this.podManager.createPod(podBaseUrl!, podSettings, allowRoot); await this.podManager.createPod(podBaseUrl!, podSettings, allowRootPod);
} catch (error: unknown) { } catch (error: unknown) {
await this.accountStore.deleteAccount(input.email); await this.accountStore.deleteAccount(input.email);
throw error; throw error;

View File

@ -33,6 +33,12 @@ export interface SetupHttpHandlerArgs {
* Renders the main view. * Renders the main view.
*/ */
templateEngine: TemplateEngine; templateEngine: TemplateEngine;
/**
* Determines if pods can be created in the root of the server.
* Relevant to make sure there are no nested storages if registration is enabled for example.
* Defaults to `true`.
*/
allowRootPod?: boolean;
} }
/** /**
@ -53,6 +59,7 @@ export class SetupHttpHandler extends OperationHttpHandler {
private readonly storageKey: string; private readonly storageKey: string;
private readonly storage: KeyValueStorage<string, boolean>; private readonly storage: KeyValueStorage<string, boolean>;
private readonly templateEngine: TemplateEngine; private readonly templateEngine: TemplateEngine;
private readonly allowRootPod: boolean;
public constructor(args: SetupHttpHandlerArgs) { public constructor(args: SetupHttpHandlerArgs) {
super(); super();
@ -62,6 +69,7 @@ export class SetupHttpHandler extends OperationHttpHandler {
this.storageKey = args.storageKey; this.storageKey = args.storageKey;
this.storage = args.storage; this.storage = args.storage;
this.templateEngine = args.templateEngine; this.templateEngine = args.templateEngine;
this.allowRootPod = args.allowRootPod ?? true;
} }
public async handle({ operation }: OperationHttpHandlerInput): Promise<ResponseDescription> { public async handle({ operation }: OperationHttpHandlerInput): Promise<ResponseDescription> {
@ -76,7 +84,7 @@ export class SetupHttpHandler extends OperationHttpHandler {
* Returns the HTML representation of the setup page. * Returns the HTML representation of the setup page.
*/ */
private async handleGet(operation: Operation): Promise<ResponseDescription> { private async handleGet(operation: Operation): Promise<ResponseDescription> {
const result = await this.templateEngine.handleSafe({ contents: {}}); const result = await this.templateEngine.handleSafe({ contents: { allowRootPod: this.allowRootPod }});
const representation = new BasicRepresentation(result, operation.target, TEXT_HTML); const representation = new BasicRepresentation(result, operation.target, TEXT_HTML);
return new OkResponseDescription(representation.metadata, representation.data); return new OkResponseDescription(representation.metadata, representation.data);
} }

View File

@ -56,29 +56,15 @@
<label> <label>
<input type="checkbox" id="createPod" name="createPod"<% <input type="checkbox" id="createPod" name="createPod"<%
if (isBlankForm || prefilled.createPod) { %> checked<% } %>> if (isBlankForm || prefilled.createPod) { %> checked<% } %>>
Create a new Pod with my WebID as owner<% if (!locals.allowRoot) { %>.<% } %> Create a new Pod with my WebID as owner<% if (locals.allowRootPod) { %> in the root<% } %>.
</label> </label>
<ol id="createPodForm"> <ol id="createPodForm">
<% if (locals.allowRoot) { %> <% if (!locals.allowRootPod) { %>
<li class="radio">
<label>
<input type="radio" id="rootPodOn" name="rootPod" value="on"<%
if (isBlankForm || prefilled.rootPod) { %> checked<% } %>>
…in the root.
</label>
</li>
<li class="radio">
<label>
<input type="radio" id="rootPodOff" name="rootPod" value=""<%
if (!isBlankForm && !prefilled.rootPod) { %> checked<% } %>>
…in its own namespace.
</label>
</li>
<% } %>
<li id="podNameForm"> <li id="podNameForm">
<label for="podName">Pod name:</label> <label for="podName">Pod name:</label>
<input id="podName" type="text" name="podName" value="<%= prefilled.podName || '' %>"> <input id="podName" type="text" name="podName" value="<%= prefilled.podName || '' %>">
</li> </li>
<% } %>
</ol> </ol>
</li> </li>
</ol> </ol>
@ -124,7 +110,7 @@
[ [
'mainForm', 'mainForm',
'createWebIdOn', 'createWebIdOff', 'createWebIdForm', 'existingWebIdForm', 'webId', 'createWebIdOn', 'createWebIdOff', 'createWebIdForm', 'existingWebIdForm', 'webId',
'createPod', 'createPodForm', 'rootPodOn', 'rootPodOff', 'podNameForm', 'podName', 'createPod', 'createPodForm', 'podNameForm', 'podName',
'register', 'passwordForm', 'register', 'passwordForm',
].forEach(registerElement); ].forEach(registerElement);
@ -133,7 +119,6 @@
createWebIdForm: () => elements.createWebIdOn.checked, createWebIdForm: () => elements.createWebIdOn.checked,
existingWebIdForm: () => elements.createWebIdOff.checked, existingWebIdForm: () => elements.createWebIdOff.checked,
createPodForm: () => elements.createPod.checked, createPodForm: () => elements.createPod.checked,
podNameForm: () => !elements.rootPodOn.checked,
}; };
// Ensures that the only relevant input fields are visible and enabled // Ensures that the only relevant input fields are visible and enabled
@ -158,7 +143,6 @@
webId.focus(); webId.focus();
break; break;
case elements.createPod: case elements.createPod:
case elements.rootPodOff:
elements.podName.focus(); elements.podName.focus();
break; break;
} }

View File

@ -3,7 +3,7 @@
<form method="post" id="mainForm"> <form method="post" id="mainForm">
<p class="error" id="error"></p> <p class="error" id="error"></p>
<%- include('./register-partial.html.ejs', { allowRoot: false }) %> <%- include('./register-partial.html.ejs', { allowRootPod: false }) %>
<p class="actions"><button type="submit" name="submit">Sign up</button></p> <p class="actions"><button type="submit" name="submit">Sign up</button></p>
</form> </form>

View File

@ -12,12 +12,13 @@
<ol> <ol>
<li class="checkbox"> <li class="checkbox">
<label> <label>
<input type="checkbox" checked disabled> <input type="checkbox" <% if (!allowRootPod) { %> checked <% } %> disabled>
Enable account registration. Enable account registration.
</label> </label>
<p> <p>
You can disable account registration This can only be changed in the configuration.
by <a href="https://github.com/CommunitySolidServer/CommunitySolidServer/blob/main/config/identity/README.md">changing the configuration</a>. See the <a href="https://github.com/CommunitySolidServer/CommunitySolidServer/blob/main/config/README.md">general configuration documentation</a>
and the <a href="https://github.com/CommunitySolidServer/CommunitySolidServer/blob/main/config/identity/README.md">identity specific options</a> to find out how.
</p> </p>
</li> </li>
<li class="checkbox"> <li class="checkbox">
@ -31,7 +32,7 @@
</li> </li>
<li class="checkbox" id="initializeForm"> <li class="checkbox" id="initializeForm">
<label> <label>
<input type="checkbox" id="initialize" name="initialize"> <input type="checkbox" id="initialize" name="initialize" <% if (!allowRootPod) { %> disabled <% } %>>
Expose a public root Pod. Expose a public root Pod.
</label> </label>
<p> <p>
@ -39,6 +40,8 @@
<br> <br>
You typically only want to choose this You typically only want to choose this
for rapid testing and development. for rapid testing and development.
<br>
This requires registration to be disabled.
</p> </p>
</li> </li>
</ol> </ol>
@ -48,7 +51,7 @@
<legend>Sign up</legend> <legend>Sign up</legend>
<%- <%-
include('../identity/email-password/register-partial.html.ejs', { include('../identity/email-password/register-partial.html.ejs', {
allowRoot: true, allowRootPod: allowRootPod,
}) })
%> %>
</fieldset> </fieldset>
@ -64,6 +67,13 @@
Object.assign(visibilityConditions, { Object.assign(visibilityConditions, {
registrationForm: () => elements.registration.checked, registrationForm: () => elements.registration.checked,
initializeForm: () => !elements.registration.checked, });
// Assigning elements to `visibilityConditions` causes the `disabled` to be removed.
// We don't want this for the initialize form.
const registration = document.getElementById('registration');
registration.addEventListener('change', () => {
const initializeForm = document.getElementById('initializeForm');
initializeForm.classList[elements.registration.checked ? 'add' : 'remove']('hidden');
}); });
</script> </script>

View File

@ -65,57 +65,57 @@ describe('A RegistrationManager', (): void => {
describe('validating data', (): void => { describe('validating data', (): void => {
it('errors on invalid emails.', async(): Promise<void> => { it('errors on invalid emails.', async(): Promise<void> => {
let input: any = { email: undefined }; let input: any = { email: undefined };
expect((): any => manager.validateInput(input)).toThrow('Please enter a valid e-mail address.'); expect((): any => manager.validateInput(input, false)).toThrow('Please enter a valid e-mail address.');
input = { email: '' }; input = { email: '' };
expect((): any => manager.validateInput(input)).toThrow('Please enter a valid e-mail address.'); expect((): any => manager.validateInput(input, false)).toThrow('Please enter a valid e-mail address.');
input = { email: 'invalidEmail' }; input = { email: 'invalidEmail' };
expect((): any => manager.validateInput(input)).toThrow('Please enter a valid e-mail address.'); expect((): any => manager.validateInput(input, false)).toThrow('Please enter a valid e-mail address.');
}); });
it('errors on invalid passwords.', async(): Promise<void> => { it('errors on invalid passwords.', async(): Promise<void> => {
const input: any = { email, webId, password, confirmPassword: 'bad' }; const input: any = { email, webId, password, confirmPassword: 'bad' };
expect((): any => manager.validateInput(input)).toThrow('Your password and confirmation did not match.'); expect((): any => manager.validateInput(input, false)).toThrow('Your password and confirmation did not match.');
}); });
it('errors on missing passwords.', async(): Promise<void> => { it('errors on missing passwords.', async(): Promise<void> => {
const input: any = { email, webId }; const input: any = { email, webId };
expect((): any => manager.validateInput(input)).toThrow('Please enter a password.'); expect((): any => manager.validateInput(input, false)).toThrow('Please enter a password.');
}); });
it('errors when setting rootPod to true when not allowed.', async(): Promise<void> => { it('errors when setting rootPod to true when not allowed.', async(): Promise<void> => {
const input = { email, password, confirmPassword, createWebId, rootPod }; const input = { email, password, confirmPassword, createWebId, rootPod };
expect((): any => manager.validateInput(input)).toThrow('Creating a root pod is not supported.'); expect((): any => manager.validateInput(input, false)).toThrow('Creating a root pod is not supported.');
}); });
it('errors when a required WebID is not valid.', async(): Promise<void> => { it('errors when a required WebID is not valid.', async(): Promise<void> => {
let input: any = { email, password, confirmPassword, register, webId: undefined }; let input: any = { email, password, confirmPassword, register, webId: undefined };
expect((): any => manager.validateInput(input)).toThrow('Please enter a valid WebID.'); expect((): any => manager.validateInput(input, false)).toThrow('Please enter a valid WebID.');
input = { email, password, confirmPassword, register, webId: '' }; input = { email, password, confirmPassword, register, webId: '' };
expect((): any => manager.validateInput(input)).toThrow('Please enter a valid WebID.'); expect((): any => manager.validateInput(input, false)).toThrow('Please enter a valid WebID.');
}); });
it('errors on invalid pod names when required.', async(): Promise<void> => { it('errors on invalid pod names when required.', async(): Promise<void> => {
let input: any = { email, webId, password, confirmPassword, createPod, podName: undefined }; let input: any = { email, webId, password, confirmPassword, createPod, podName: undefined };
expect((): any => manager.validateInput(input)).toThrow('Please specify a Pod name.'); expect((): any => manager.validateInput(input, false)).toThrow('Please specify a Pod name.');
input = { email, webId, password, confirmPassword, createPod, podName: ' ' }; input = { email, webId, password, confirmPassword, createPod, podName: ' ' };
expect((): any => manager.validateInput(input)).toThrow('Please specify a Pod name.'); expect((): any => manager.validateInput(input, false)).toThrow('Please specify a Pod name.');
input = { email, webId, password, confirmPassword, createWebId }; input = { email, webId, password, confirmPassword, createWebId };
expect((): any => manager.validateInput(input)).toThrow('Please specify a Pod name.'); expect((): any => manager.validateInput(input, false)).toThrow('Please specify a Pod name.');
}); });
it('errors when no option is chosen.', async(): Promise<void> => { it('errors when no option is chosen.', async(): Promise<void> => {
const input = { email, webId, password, confirmPassword }; const input = { email, webId, password, confirmPassword };
expect((): any => manager.validateInput(input)).toThrow('Please register for a WebID or create a Pod.'); expect((): any => manager.validateInput(input, false)).toThrow('Please register for a WebID or create a Pod.');
}); });
it('adds the template parameter if there is one.', async(): Promise<void> => { it('adds the template parameter if there is one.', async(): Promise<void> => {
const input = { email, webId, password, confirmPassword, podName, template: 'template', createPod }; const input = { email, webId, password, confirmPassword, podName, template: 'template', createPod };
expect(manager.validateInput(input)).toEqual({ expect(manager.validateInput(input, false)).toEqual({
email, email,
webId, webId,
password, password,
@ -146,12 +146,12 @@ describe('A RegistrationManager', (): void => {
register, register,
createPod, createPod,
}; };
expect(manager.validateInput(input)).toEqual({ expect(manager.validateInput(input, false)).toEqual({
email, password: ' a ', podName, template: 'template', createWebId, register, createPod, rootPod: false, email, password: ' a ', podName, template: 'template', createWebId, register, createPod, rootPod: false,
}); });
input = { email, webId: ` ${webId} `, password: ' a ', confirmPassword: ' a ', register: true }; input = { email, webId: ` ${webId} `, password: ' a ', confirmPassword: ' a ', register: true };
expect(manager.validateInput(input)).toEqual({ expect(manager.validateInput(input, false)).toEqual({
email, webId, password: ' a ', createWebId: false, register, createPod: false, rootPod: false, email, webId, password: ' a ', createWebId: false, register, createPod: false, rootPod: false,
}); });
}); });
@ -160,7 +160,7 @@ describe('A RegistrationManager', (): void => {
describe('handling data', (): void => { describe('handling data', (): void => {
it('can register a user.', async(): Promise<void> => { it('can register a user.', async(): Promise<void> => {
const params: any = { email, webId, password, register, createPod: false, createWebId: false }; const params: any = { email, webId, password, register, createPod: false, createWebId: false };
await expect(manager.register(params)).resolves.toEqual({ await expect(manager.register(params, false)).resolves.toEqual({
email, email,
webId, webId,
oidcIssuer: baseUrl, oidcIssuer: baseUrl,
@ -184,7 +184,7 @@ describe('A RegistrationManager', (): void => {
it('can create a pod.', async(): Promise<void> => { it('can create a pod.', async(): Promise<void> => {
const params: any = { email, webId, password, podName, createPod, createWebId: false, register: false }; const params: any = { email, webId, password, podName, createPod, createWebId: false, register: false };
await expect(manager.register(params)).resolves.toEqual({ await expect(manager.register(params, false)).resolves.toEqual({
email, email,
webId, webId,
oidcIssuer: baseUrl, oidcIssuer: baseUrl,
@ -211,7 +211,7 @@ describe('A RegistrationManager', (): void => {
it('adds an oidcIssuer to the data when doing both IDP registration and pod creation.', async(): Promise<void> => { it('adds an oidcIssuer to the data when doing both IDP registration and pod creation.', async(): Promise<void> => {
const params: any = { email, webId, password, confirmPassword, podName, register, createPod, createWebId: false }; const params: any = { email, webId, password, confirmPassword, podName, register, createPod, createWebId: false };
podSettings.oidcIssuer = baseUrl; podSettings.oidcIssuer = baseUrl;
await expect(manager.register(params)).resolves.toEqual({ await expect(manager.register(params, false)).resolves.toEqual({
email, email,
webId, webId,
oidcIssuer: baseUrl, oidcIssuer: baseUrl,
@ -240,7 +240,7 @@ describe('A RegistrationManager', (): void => {
const params: any = { email, webId, password, confirmPassword, podName, register, createPod }; const params: any = { email, webId, password, confirmPassword, podName, register, createPod };
podSettings.oidcIssuer = baseUrl; podSettings.oidcIssuer = baseUrl;
(podManager.createPod as jest.Mock).mockRejectedValueOnce(new Error('pod error')); (podManager.createPod as jest.Mock).mockRejectedValueOnce(new Error('pod error'));
await expect(manager.register(params)).rejects.toThrow('pod error'); await expect(manager.register(params, false)).rejects.toThrow('pod error');
expect(ownershipValidator.handleSafe).toHaveBeenCalledTimes(1); expect(ownershipValidator.handleSafe).toHaveBeenCalledTimes(1);
expect(ownershipValidator.handleSafe).toHaveBeenLastCalledWith({ webId }); expect(ownershipValidator.handleSafe).toHaveBeenLastCalledWith({ webId });
@ -263,7 +263,7 @@ describe('A RegistrationManager', (): void => {
podSettings.webId = generatedWebID; podSettings.webId = generatedWebID;
podSettings.oidcIssuer = baseUrl; podSettings.oidcIssuer = baseUrl;
await expect(manager.register(params)).resolves.toEqual({ await expect(manager.register(params, false)).resolves.toEqual({
email, email,
webId: generatedWebID, webId: generatedWebID,
oidcIssuer: baseUrl, oidcIssuer: baseUrl,