I recently had to use the built-in deleteweb command to delete a web site and was irritated to find that the command wouldn’t let me delete the web because it had sub-webs. I simply couldn’t live with that as it’s extremely frustrating to have to delete all the child webs one at a time. So I created a better deleteweb command, called simply gl-deleteweb2. It behaves exactly like the built-in deleteweb command except that you can pass in a “recurse” switch to have it delete recursively (delete the web and all it’s children). What was really nice is that it took me literally 2 minutes to create this command (nice change from some of the more challenging ones I’ve had lately).

The code is extremely simple:

 1/// <summary>
 2/// Runs the specified command.
 3/// </summary>
 4/// <param name="command">The command.</param>
 5/// <param name="keyValues">The key values.</param>
 6/// <param name="output">The output.</param>
 7/// <returns></returns>
 8public override int Run(string command, StringDictionary keyValues, out string output)
 9{
10    output = string.Empty;
11
12    InitParameters(keyValues);
13
14    string url = Params["url"].Value.TrimEnd('/');
15
16    using (SPSite site = new SPSite(url))
17    using (SPWeb web = site.OpenWeb())
18    {
19        if (web.IsRootWeb)
20        {
21            throw new SPException(SPResource.GetString("CannotDelRootwebByDelweb", new object[0]));
22        }
23
24        if (web.Webs.Count > 0 && !Params["recurse"].UserTypedIn)
25        {
26            throw new SPException(
27                string.Format(
28                    "Error deleting Web site \"{0}\".  You can't delete a site that has subsites unless you pass the \"recurse\" flag into the command.",
29                    web.ServerRelativeUrl));
30        }
31
32        if (web.Webs.Count > 0 && Params["recurse"].UserTypedIn)
33            DeleteSubWebs(web.Webs);
34
35        web.Delete();
36
37    }
38
39    return 1;
40}
41 
42#endregion
43 
44/// <summary>
45/// Deletes the sub webs.
46/// </summary>
47/// <param name="webs">The webs.</param>
48private static void DeleteSubWebs(SPWebCollection webs)
49{
50    foreach (SPWeb web in webs)
51    {
52        if (web.Webs.Count > 0)
53            DeleteSubWebs(web.Webs);
54
55        web.Delete();
56    }
57}

Use this command just like deleteweb but pass in -recurse if you want to delete a web with sub-webs (this keeps the action explicit so the user understands that it will delete all sub-webs). The syntax of the command can be seen below:

C:\>stsadm -help gl-deleteweb2

stsadm -o gl-deleteweb2

Deletes a web.

Parameters:
        -url <url of web to delete>
        [-recurse (delete all sub-sites)]

Here’s an example of how to delete a web recursively:

stsadm –o gl-deleteweb2 -url "http://intranet/WebWithChildren" -recurse