Программно сохранить форму InfoPath браузера в исходный список - PullRequest
1 голос
/ 04 марта 2010

У меня есть форма InfoPath в библиотеке форм в MOSS 2007. Я думаю, что панель инструментов браузера InfoPath с ее сохранением (вводом имени файла вручную) и закрытием довольно усложняет процесс заполнения формы. То, что я пытаюсь сделать, это просто иметь кнопку с некоторым кодом, который сохраняет форму в библиотеке, где она была открыта с автоматически сгенерированным именем файла и закрывается обратно в библиотеку. Для этого я написал следующий код:

public void SaveForm(string formXml, string fileName, Dictionary<string, string> extraColumns)
{
    SPFolder formsLibraryFolder = SPContext.Current.List.RootFolder;

    string lowerCaseFilename = fileName.ToLower();
    if (!lowerCaseFilename.EndsWith(".xml"))
        fileName += ".xml";

    web.AllowUnsafeUpdates = true;
    SPFile file = formsLibraryFolder.Files.Add(fileName, Encoding.UTF8.GetBytes(formXml));

    if ((extraColumns != null) && (extraColumns.Count > 0))
    {
        foreach (KeyValuePair<string, string> column in extraColumns)
        {
            file.Item[column.Key] = column.Value;
        }
        file.Item.Update();
    }

    web.AllowUnsafeUpdates = false;
}

Проблема с этим кодом, как выясняется, заключается в том, что SPContext.Current.List является нулевым в ситуации, когда я хочу сохранить форму в библиотеке, в которой она была открыта. Я явно ошибочно предположил, что, поскольку форма будет заполнена в браузере, контекст списка будет действительным. Однако я могу получить доступ к SPWeb, который содержит список, но это означает, что мне нужно было бы жестко закодировать имя списка для каждого типа формы и, конечно, заранее знать имя списка, в которое входит каждая форма. Этот код является частью вспомогательной библиотеки, которую я написал, и ссылаюсь во многих формах на разные проекты, так что я действительно не могу быть жестким кодом. Конечно, я мог бы передать имя списка в качестве аргумента и жестко закодировать имя списка в самой форме, но это все равно означает, что мне нужно заранее знать, где будет развернута форма. Можно ли как-нибудь выяснить, в какой библиотеке была нажата новая, чтобы начать заполнение формы?

1 Ответ

3 голосов
/ 04 марта 2010

Я разобрался, как это сделать, поэтому выложу для всех.

Когда вы закрываете форму браузера, InfoPath перенаправляет вас обратно в список. Вы можете получить URL к списку благодаря методу 2 в следующей статье:

http://www.bizsupportonline.net/blog/2010/01/2-ways-retrieve-sharepoint-site-collection-infopath-browser-form/

Когда нажимается моя собственная кнопка сохранения, я передаю URL своей обновленной функции сохранения. Я должен отметить, что это не защищенный от ошибок код, и есть несколько мест, которые он может сломать. Однако он работает для конкретных случаев, когда мне нужно его использовать.

public void SaveForm(string formXml, string fileName, string url, Dictionary<string, string> extraColumns)
{
    SPWeb web = SPContext.Current.Web;
    string webUrl = web.Url;
    if (!webUrl.EndsWith("/"))
        webUrl += "/";

    string relativeUrl = url.Replace(webUrl, string.Empty);
    string listName = relativeUrl.Substring(0, relativeUrl.IndexOf('/'));
    SPList destinationList = web.Lists[listName];
    SPFolder destinationFolder = destinationList.RootFolder;

    string lowerCaseFilename = fileName.ToLower();
    if (!lowerCaseFilename.EndsWith(".xml"))
        fileName += ".xml";

    web.AllowUnsafeUpdates = true;
    SPFile file = destinationFolder.Files.Add(fileName, Encoding.UTF8.GetBytes(formXml));

    if ((extraColumns != null) && (extraColumns.Count > 0))
    {
        foreach (KeyValuePair<string, string> column in extraColumns)
        {
            file.Item[column.Key] = column.Value;
        }
        file.Item.Update();
    }

    web.AllowUnsafeUpdates = false;
}
...