Robert McMurray's Blog [MSFT]

Discussing IIS, FTP, WebDAV, FPSE, WMI, ADSI, ISAPI, ASP, Java, FastCGI, etc. ;-)

FTP 7.5 and WebDAV 7.5 have been released!

FTP 7.5 and WebDAV 7.5 have been released!

Rate This
  • Comments 5

Over the next few days you're going to hear a lot of details about many of the great new IIS extensions that the IIS feature team is releasing for the 2009 MIX Conference in Las Vegas later today. I don't want to spoil any surprises by talking about anyone else’s feature areas, but I’m about to board a plane to head out on vacation (to Peru!) and I'm not taking a computer with me (believe it or not!) so I thought that I’d take a moment to highlight just a few of the features that are in the FTP 7.5 and WebDAV 7.5 releases.

FTP 7.5

One of the great new features in FTP 7.5 is extensibility. We had some extensibility features that were partially implemented in FTP 7.0, and we used those for the ASP.NET and IIS Manager authentication providers, but FTP extensibility was not officially supported in the 7.0 release. With FTP 7.5 extensibility is fully supported, so you can now write providers that implement custom functionality for authentication/authorization, home directory lookups, and logging.

To help developers get started writing providers for FTP 7.5, I wrote the following walkthroughs that are available on Microsoft's learn.iis.net web site:

Another highlight in FTP 7.5 is the addition of a user interface for the FTP Request Filtering features. We shipped request filtering with FTP 7.0 while the request filtering user interface was still in development, and the 7.5 version seemed like a great time to release it.

For those of you that are unfamiliar with FTP request filtering, it allows you to add rules that allow or deny specific file extensions, hidden segments, URL sequences, and even FTP commands.

For more information about the features in the new FTP service, see the following page on the http://www.iis.net/ web site:

http://www.iis.net/extensions/FTP

WebDAV 7.5

One of the big changes in WebDAV 7.5 is the inclusion of WebDAV locks, which are implemented through a simple locking mechanism. Our lock implementation was still in development when we shipped the WebDAV 7.0 release, and this release should help publishing scenarios where WebDAV locks are required.

To help you get started using locks with WebDAV 7.5, I wrote the following walkthrough that is available on Microsoft's learn.iis.net web site:

How to Use WebDAV Locks

For more information about the features in the new WebDAV module, see the following page on the http://www.iis.net/ web site:

http://www.iis.net/extensions/WebDAV

In Closing...

So that about wraps it up for some of the major highlights for FTP and WebDAV; for news about everything else that's coming out for IIS, watch the news items on the http://www.iis.net/ home page!

Comments
  • How can you handle the user rights? I need  to create a provider, that seems easy, but also need to tell wich user can read and wich user can write and to with folders... wich is the best method?

    Everything should be programmatically, not using the IIS control pannel.

    thanks!

  • An extensibility provider provides user and role/group lookups - user rights are implemented through the built-in authorization settings. So from a programmatic point of view, you can script your authorization rules outside of the IIS Manager UI. For example, if you create the example authentication provider that I describe in the following walkthrough:

    http://learn.iis.net/page.aspx/598/how-to-use-managed-code-to-create-a-simple-ftp-authentication-provider/

    You could use the following APPCMD syntax to add access rules for the user and role:

    appcmd.exe set config "Default Web Site" -section:system.ftpServer/security/authorization /+"[accessType='Allow',users='MyUser',permissions='Read, Write']" /commit:apphost

    appcmd.exe set config "Default Web Site" -section:system.ftpServer/security/authorization /+"[accessType='Allow',roles='MyRole',permissions='Read']" /commit:apphost

    Or you could use JavaScript:

    var adminManager = new ActiveXObject('Microsoft.ApplicationHost.WritableAdminManager');
    adminManager.CommitPath = "MACHINE/WEBROOT/APPHOST";
    var authorizationSection = adminManager.GetAdminSection("system.ftpServer/security/authorization", "MACHINE/WEBROOT/APPHOST/Default Web Site");
    var authorizationCollection = authorizationSection.Collection;

    var addElement = authorizationCollection.CreateNewElement("add");
    addElement.Properties.Item("accessType").Value = "Allow";
    addElement.Properties.Item("users").Value = "MyUser";
    addElement.Properties.Item("permissions").Value = "Read, Write";
    authorizationCollection.AddElement(addElement);

    var addElement1 = authorizationCollection.CreateNewElement("add");
    addElement1.Properties.Item("accessType").Value = "Allow";
    addElement1.Properties.Item("roles").Value = "MyRole";
    addElement1.Properties.Item("permissions").Value = "Read";
    authorizationCollection.AddElement(addElement1);

    adminManager.CommitChanges();

    Or you could use managed-code:

    using System;
    using System.Text;
    using Microsoft.Web.Administration;

    internal static class Sample {

      private static void Main() {

        using(ServerManager serverManager = new ServerManager()) {
          Configuration config = serverManager.GetApplicationHostConfiguration();

          ConfigurationSection authorizationSection = config.GetSection("system.ftpServer/security/authorization", "Default Web Site");

          ConfigurationElementCollection authorizationCollection = authorizationSection.GetCollection();

          ConfigurationElement addElement = authorizationCollection.CreateElement("add");
          addElement["accessType"] = @"Allow";
          addElement["users"] = @"MyUser";
          addElement["permissions"] = @"Read, Write";
          authorizationCollection.Add(addElement);

          ConfigurationElement addElement1 = authorizationCollection.CreateElement("add");
          addElement1["accessType"] = @"Allow";
          addElement1["roles"] = @"MyRole";
          addElement1["permissions"] = @"Read";
          authorizationCollection.Add(addElement1);

          serverManager.CommitChanges();
        }
      }
    }

  • Hi Robert, thanks for useful post! I use FTPLogging provider for logging with GEOIP locations. I have a question about manual FTP session disconnecting.

    I need disconnect one FTP session by "session ID" programatically using managed code. Within IIS Manager console it's easy but i can not find documentation on MSDN or other source how to this programatically. Got any idea please?

    I apologize for my English.

  • You can terminate a session programmatically using code like the following example. Please note that this code works great in a standalone application, like a console application that takes the site name and session ID as parameters. That being said, this code will not work inside an FTP provider because you need to be logged on with administrative access in order to terminate an FTP session. I have a way to make this code work inside a provider, but I still have some security-related questions that I want to discuss with our security group before I would put that example in a walkthrough that customers can use.

      private void TerminateSession(string siteName, string sessionId)
      {
         try
         {
            using (ServerManager serverManager = new ServerManager())
            {
               Configuration config = serverManager.GetApplicationHostConfiguration();
               ConfigurationSection sitesSection = config.GetSection("system.applicationHost/sites");
               ConfigurationElementCollection sitesCollection = sitesSection.GetCollection();
               ConfigurationElement siteElement = FindElement(sitesCollection, "site", "name", siteName);
               if (siteElement == null) throw new InvalidOperationException("Element not found!");
               ConfigurationElement ftpServerElement = siteElement.GetChildElement("ftpServer");
               ConfigurationElementCollection ftpSessions = ftpServerElement.GetCollection("sessions");
               ConfigurationElement sessionElement = FindElement(ftpSessions, "session", "sessionId", sessionId);
               if (sessionElement == null) throw new InvalidOperationException("Element not found!");
               ConfigurationMethodInstance ftpTerminateMethod = sessionElement.Methods["Terminate"].CreateInstance();
               ftpTerminateMethod.Execute();
            }
         }
         catch (Exception ex)
         {
            Debug.WriteLine(ex.Message);
         }
      }
      private static ConfigurationElement FindElement(ConfigurationElementCollection collection, string elementTagName, params string[] keyValues)
      {
         foreach (ConfigurationElement element in collection)
         {
            if (String.Equals(element.ElementTagName, elementTagName, StringComparison.OrdinalIgnoreCase))
            {
               bool matches = true;
               for (int i = 0; i < keyValues.Length; i += 2)
               {
                  object o = element.GetAttributeValue(keyValues[i]);
                  string value = null;
                  if (o != null)
                  {
                     value = o.ToString();
                  }
                  if (!String.Equals(value, keyValues[i + 1], StringComparison.OrdinalIgnoreCase))
                  {
                     matches = false;
                     break;
                  }
               }
               if (matches)
               {
                  return element;
               }
            }
         }
         return null;
      }
  • I've been following along and cannot get my code to work properly.  How can I debug whats going on with my DLL?

Page 1 of 1 (5 items)
Leave a Comment
  • Please add 3 and 7 and type the answer here:
  • Post