diff --git a/docs/sp/files.md b/docs/sp/files.md index 32530a1b6..be8712eef 100644 --- a/docs/sp/files.md +++ b/docs/sp/files.md @@ -376,3 +376,31 @@ import { IFile } from "@pnp/sp/files"; const file: IFile = sp.web.getFileById("2b281c7b-ece9-4b76-82f9-f5cf5e152ba0"); ``` + +### delete + +Deletes a file + +```TypeScript +import { sp } from "@pnp/sp"; +import "@pnp/sp/webs"; +import "@pnp/sp/files"; + +await sp.web.rootFolder.files.getByName("name.txt").delete(); +``` + +### delete with params + +_Added in 2.0.9_ + +Deletes a file with options + +```TypeScript +import { sp } from "@pnp/sp"; +import "@pnp/sp/webs"; +import "@pnp/sp/files"; + +await sp.web.rootFolder.files.getByName("name.txt").deleteWithParams({ + BypassSharedLock: true, +}); +``` diff --git a/docs/sp/folders.md b/docs/sp/folders.md index b31418bd9..291fd9a89 100644 --- a/docs/sp/folders.md +++ b/docs/sp/folders.md @@ -167,6 +167,35 @@ const destinationUrl = `/sites/my-site/SiteAssets/new-folder`; await sp.web.rootFolder.folders.getByName("SiteAssets").folders.getByName("My Folder").copyByPath(destinationUrl, true); ``` +### delete + +Deletes a folder + +```TypeScript +import { sp } from "@pnp/sp"; +import "@pnp/sp/webs"; +import "@pnp/sp/folders"; + +await sp.web.rootFolder.folders.getByName("My Folder").delete(); +``` + +### delete with params + +_Added in 2.0.9_ + +Deletes a folder with options + +```TypeScript +import { sp } from "@pnp/sp"; +import "@pnp/sp/webs"; +import "@pnp/sp/folders"; + +await sp.web.rootFolder.folders.getByName("My Folder").deleteWithParams({ + BypassSharedLock: true, + DeleteIfEmpty: true, + }); +``` + ### recycle Recycles a folder diff --git a/docs/sp/items.md b/docs/sp/items.md index a2aa04a2d..71cd8a46a 100644 --- a/docs/sp/items.md +++ b/docs/sp/items.md @@ -419,6 +419,27 @@ let list = sp.web.lists.getByTitle("MyList"); await list.items.getById(1).delete(); ``` +## Delete With Params + +_Added in 2.0.9_ + +Deletes the item object with options. + +```TypeScript +import { sp } from "@pnp/sp"; +import "@pnp/sp/webs"; +import "@pnp/sp/lists"; +import "@pnp/sp/items"; + +let list = sp.web.lists.getByTitle("MyList"); + +await list.items.getById(1).deleteWithParams({ + BypassSharedLock: true, + }); +``` + +> The deleteWithParams method can only be used by accounts where UserToken.IsSystemAccount is true + ## Resolving field names It's a very common mistake trying wrong field names in the requests. diff --git a/packages/sp/files/types.ts b/packages/sp/files/types.ts index 474e005da..6f51c1f29 100644 --- a/packages/sp/files/types.ts +++ b/packages/sp/files/types.ts @@ -317,6 +317,16 @@ export class _File extends _SharePointQueryableInstance { return spPost(this.clone(File, "recycle")); } + /** + * Deletes the file object with options. + * + * @param parameters Specifies the options to use when deleting a file. + */ + @tag("fi.del-params") + public async deleteWithParams(parameters: Partial): Promise { + return spPost(this.clone(File, "DeleteWithParameters"), body({ parameters })); + } + /** * Reverts an existing checkout for the file. * @@ -683,3 +693,19 @@ export interface IFileInfo { UIVersionLabel: string; UniqueId: string; } + +export interface IFileDeleteParams { + /** + * If true, delete or recyle a file when the LockType + * value is SPLockType.Shared or SPLockType.None. + * When false, delete or recycle the file when + * the LockType value SPLockType.None. + */ + BypassSharedLock: boolean; + + /** + * Gets or sets a string value that allows SPfile delete and recycle methods + * to target a file with a matching value. Use null to unconditionally delete the file. + */ + ETagMatch: string; +} diff --git a/packages/sp/folders/types.ts b/packages/sp/folders/types.ts index 1902ad232..7405e7469 100644 --- a/packages/sp/folders/types.ts +++ b/packages/sp/folders/types.ts @@ -246,6 +246,16 @@ export class _Folder extends _SharePointQueryableInstance { })); } + /** + * Deletes the folder object with options. + * + * @param parameters Specifies the options to use when deleting a folder. + */ + @tag("f.del-params") + public async deleteWithParams(parameters: Partial): Promise { + return spPost(this.clone(Folder, "DeleteWithParameters"), body({ parameters })); + } + /** * Gets the shareable item associated with this folder */ @@ -313,3 +323,28 @@ export interface IFolderInfo { UniqueId: string; WelcomePage: string; } + +export interface IFolderDeleteParams { + + + /** + * If true, delete or recycle a folder iff all files have + * LockType values SPLockType.Shared or SPLockType.None. + * When false, delete or recycle the folder if all files + * have the LockType value SPLockType.None. See the enum. + */ + BypassSharedLock: boolean; + + /** + * Gets or sets a string value that allows SPFolder delete + * and recycle methods to target a folder with a matching value + */ + ETagMatch: string; + + /** + * Gets or sets a Boolean that controls the way in which folders + * are deleted. If set to true, only empty folders will be deleted. + * If set to false, folders that are not empty may be deleted. + */ + DeleteIfEmpty: boolean; +} diff --git a/packages/sp/items/types.ts b/packages/sp/items/types.ts index 972e07e40..23a0a93f2 100644 --- a/packages/sp/items/types.ts +++ b/packages/sp/items/types.ts @@ -261,6 +261,16 @@ export class _Item extends _SharePointQueryableInstance { return spPost(this.clone(Item, "recycle")); } + /** + * Deletes the item object with options. + * + * @param parameters Specifies the options to use when deleting a item. + */ + @tag("i.del-params") + public async deleteWithParams(parameters: Partial): Promise { + return spPost(this.clone(Item, "DeleteWithParameters"), body({ parameters })); + } + /** * Gets a string representation of the full URL to the WOPI frame. * If there is no associated WOPI application, or no associated action, an empty string is returned. @@ -411,3 +421,14 @@ export interface IItemUpdateResult { export interface IItemUpdateResultData { "odata.etag": string; } + +export interface IItemDeleteParams { + + /** + * If true, delete or recycle a file when the LockType + * value is SPLockType.Shared or SPLockType.None. + * When false, delete or recycle the file when + * the LockType value SPLockType.None. + */ + BypassSharedLock: boolean; +} diff --git a/test/sp/files.ts b/test/sp/files.ts index 58e9ae5ac..87547b9ae 100644 --- a/test/sp/files.ts +++ b/test/sp/files.ts @@ -171,6 +171,20 @@ describe("file", () => { expect(r.length).to.eq(0); }); + it("delete file with params", async function () { + const name = `Testing Delete - ${getRandomString(4)}.txt`; + await files.add(name, "Some test text content."); + let r = await files.filter(`Name eq '${name}'`)(); + expect(r.length).to.eq(1); + + await files.getByName(name).deleteWithParams({ + BypassSharedLock: true, + }); + + r = await files.filter(`Name eq '${name}'`)(); + expect(r.length).to.eq(0); + }); + it("listItemAllFields", function () { return expect(files.getByName(testFileName).listItemAllFields()).to.be.fulfilled; diff --git a/test/sp/folders.ts b/test/sp/folders.ts index 3f535888c..5179ae771 100644 --- a/test/sp/folders.ts +++ b/test/sp/folders.ts @@ -96,8 +96,23 @@ describe("Folder", () => { }); it("recycles folder", async function () { - await web.rootFolder.folders.getByName("SiteAssets").folders.add("test3"); - return expect(web.rootFolder.folders.getByName("SiteAssets").folders.getByName("test").recycle()).to.eventually.be.fulfilled; + const name = `test_${getRandomString(7)}`; + await web.rootFolder.folders.getByName("SiteAssets").folders.add(name); + return expect(web.rootFolder.folders.getByName("SiteAssets").folders.getByName(name).recycle()).to.eventually.be.fulfilled; + }); + + it("delete folder with params", async function () { + const name = `test_${getRandomString(7)}`; + const folders = web.rootFolder.folders.getByName("SiteAssets").folders; + await folders.add(name); + + await folders.getByName(name).deleteWithParams({ + BypassSharedLock: true, + DeleteIfEmpty: true, + }); + + const r = await folders.filter(`Name eq '${name}'`)(); + expect(r.length).to.eq(0); }); it("should get server relative url", function () { diff --git a/test/sp/items.ts b/test/sp/items.ts index 018c09e45..20a32fd31 100644 --- a/test/sp/items.ts +++ b/test/sp/items.ts @@ -118,6 +118,25 @@ describe("Items", () => { return expect(item.item.recycle()).to.eventually.be.fulfilled; }); + /** + * Skipped because only system accounts can call this method for items. + */ + it.skip("delete item with params", async function () { + + const title = `test_delparams_${getRandomString(4)}`; + + const item = await list.items.add({ + Title: title, + }); + + await item.item.deleteWithParams({ + BypassSharedLock: false, + }); + + const r = await list.items.filter(`Title eq '${title}'`)(); + expect(r.length).to.eq(0); + }); + it("getWopiFrameUrl", async function () { const item = await list.items.select("Id").top(1)().then(r => r[0]);