Creating Sharepoint Directory Recurisvely - sharepoint

I am attempting to create a set of folders that comes in from a flat file in the manner of.
X/Y/Z
and I would like to create a directory for each of these but my memory of recursion has got me in knotts.
here is my code can someone advise.
public void CreateDirectory(SPFolderCollection oWeb, string folder)
{
SPFolder theFolder = oWeb.Add(folder);
theFolder.Update();
}
public void FolderCreator(SPWeb oWeb)
{
StreamReader reader = new StreamReader(this.txtFolders.Text);
while (reader.Peek() != -1)
{
string folderLine = reader.ReadLine();
if (folderLine.Contains("/"))
{
SPFolderCollection collection = oWeb.Folders["Documents"].SubFolders[folderLine.Split('/')[0]].SubFolders;
CreateDirectory(collection, folderLine);
}
SPFolderCollection newCollection = oWeb.Folders["Documents"].SubFolders;
CreateDirectory(newCollection, folderLine);
}
}
This does not work I am looking for it to do recrusion so if I pass
ABC/DEF/GHI
and
ABC/DEF
it will go and create the folders appropriately.
But I am stuck as how to do that.

The SPFileCollection.Add() methods allow you to pass in the full relative path of a file. So this may be an option assuming you aren't just generating a folder structure, which you may be doing, in which case this won't really work unless you create a temporary file and then delete it to keep the folder path.
web.Files.Add("/sites/somesite/shared documents/foldera/folderb/folderc/somefile.txt", stream);

Related

preprocess csv files to convert key values to lowercase when using Hybris hotfolder

CSV files are having data in uppercase for keys like UID, is there a way to convert UID to lowercase and save when using hot folder in hybris. A change on our data source will take more time than hybris change.
I am thinking of creating a LowerCaseValueTranslator for impex. is it a good approach?
I have explored LowerCaseValueTranslator path.
#Override
public Object importValue(final String valueExpr, final Item toItem) throws JaloInvalidParameterException
{
clearStatus();
Double result = null;
if (!StringUtils.isBlank(valueExpr))
{
try
{
result = valueExpr.toLowerCase();
}
catch (final NumberFormatException exc)
{
setError();
}
}
return result;
}
}
I expect that it will work - is this the best approach to do this
Is the data/UID autogenerated by Hybris, or is it a custom value from user?
In any case, a translator is a good approach to do what you want (assuming the data is a custom value). If it is autogenerated by Hybris, I would keep it as-is.

Renamed the "Modify By" field after using Elevated Mode

I'm currently facing to an issue using the Elevated Mode used in a Feature.
I have created a custome SharePoint security role (contribute role without the Delete right).
The goal of my SharePoint feature is the following:
When uploading a file to a SP Site, the name of the file needs to be renamed using the meta-data's selected. When uploading a file, a second form is asking the user to defined 3 or 4 meta-data's.
To rename the file, i have developed the following code:
Public override void ItemAdded(SPItemEventProperties properties)
{
SPSecurity.RunWithElevatedPrivileges(delegate()
{
CallFunctionToUpdate();
});
}
Public override void ItemUpdated(SPItemEventProperties properties)
{
SPSecurity.RunWithElevatedPrivileges(delegate()
{
CallFunctionToUpdate();
});
}
Public void CallFunctionToUpdate()
{
try
{
this.EventFiringEnabled = false;
using (SPWeb newWeb = newSite.OpenWeb(_properties.RelativeWebUrl))
{
SPListItem item = newWeb.Lists[_properties.ListId].GetItemById(_properties.ListItem.ID);
newFileName = FilenameManagementHelper.GenerateFilename(properties.ListItem);
currentName = properties.ListItem["Name"].ToString();
var extension = Path.GetExtension(currentName);
if (item["Title"] == null || item["Title"].ToString() != newFileName)
{
item["Title"] = newFileName;
item["Editor"] = new SPFieldUserValue(properties.OpenWeb(), properties.OpenWeb().CurrentUser.ID, properties.OpenWeb().CurrentUser.LoginName);
item.SystemUpdate();
}
if (currentName.Substring(0, currentName.Length - extension.Length) != newFileName)
{
SPList list = newWeb.Lists[_properties.List.Title];
string destUrl = list.RootFolder.Url + "/" + newFileName + extension;
SPFile fileToMove = list.Items[_properties.ListItemUniqueId].File;
SPFolder folder = newWeb.GetFolder(list.RootFolder.Url);
byte[] bin = fileToMove.OpenBinary();
folder.Files.Add(destUrl, bin, fileToMove.Properties, true);
fileToMove.Delete(); newWeb.Lists[list.RootFolder.Url].Update();
}
}
}
catch (Exception ex)
{
DocumentDiagnosticService.LogError(CategoryID.Error, string.Format("Error {0} for the file name - {1}", ex.Message, currentName));
}
finally
{
this.EventFiringEnabled = true;
}
}
Before renaming the file name, I'm updating the field (meta-data's) title and Editor. The second step will move the file (with the meta-data's and the history associated to the uploaded file)
I'm using the Elevated Mode because the user with a restricted Security role cannot delete. In the code developed I'm moving the file renamed and deleting the old file uploaded.
I found that approach because I need to keep the versioning. Updating directly the name of the file (like for the title) is not allowed and that's losing the history. Ex: A file will be uploaded, the name of the file will be updated using the Meta-data's. For the first version, there is no issue. Uploading a second file with the same meta-data's as there is already an existing file with the same name, that will generate an error. Using the Files.Add, that will oerride the current file and will keep the history.
My issue in this case: When the user is uploading the file, the fields Title and Editor are correctly replaced. Than is moving the file, renaming the field Name and deleting the old version. At this moment, the Modify by field is coming the SharePoint Sys Admin all the time.
How can i keep the Modifiy by with the name of the person who is uploading the file ?
EDIT:
Using the following code:
SPList list = newWeb.Lists[_properties.List.Title];
string destUrl = list.RootFolder.Url + "/" + newFileName + extension;
SPFile fileToMove = list.Items[_properties.ListItemUniqueId].File;
SPFolder folder = newWeb.GetFolder(list.RootFolder.Url);
byte[] bin = fileToMove.OpenBinary();
folder.Files.Add(destUrl, bin, fileToMove.Properties, true);
fileToMove.Delete();
Allow me to move the file with the meta-data's selected during the upload. I still have the versioning if a current version is already uploaded BUT the Modified By is SysAdmin.
Using the following code:
SPList list = newWeb.Lists[_properties.List.Title];
string destUrl = list.RootFolder.Url + "/" + newFileName + extension;
SPFile fileToMove = list.Items[_properties.ListItemUniqueId].File;
SPFolder folder = newWeb.GetFolder(list.RootFolder.Url);
byte[] bin = fileToMove.OpenBinary();
SPUser author = fileToMove.Author;
folder.Files.Add(destUrl, bin, author, author, DateTime.Now, DateTime.Now);
fileToMove.Delete();
Allow me to move the file and keep the history if i already have a version. I can now get the Modified By field filled by the real user who is uploading and not the SysAdmin BUT I'm losing the meta-data's selected during the upload.
Thank you for your support,
Fix.
Use item.Update() instead of SystemUpdate(). It should retain the identity of logged in user.
Thank you for your support.
I have solved my issue by using the following code:
folder.Files.Add(destUrl, bin, fileToMove.Properties, author, author, DateTime.Now, DateTime.Now, true);
Now, I have the Modified By value filled with the user who is uploading, the meta-data's are still there and the versioning too.

how create document and library in liferay

Requirement: Adding Parent folders, Child folders and Their files to Document and Library from Particular location.
Case-1: If Folder is already exists then get that id and add file
( Here I am using
addFileEntry(repositoryId, folderId,sourceFileName, mimeType, title, description, changeLog, is, size, serviceContext) of DLAppServiceUtil class ).
Case-2: If Folder is not exits add folder then add file
(Here I am using for adding folder
addFolder() method of DLAppServiceUtil class)
My case its gives slow performance. That is the problem.
Which version of Liferay are you using?
The current trend is the following in 6.1+ (well, when it is correctly implemented, but you can build more or less on this with the new DLApp implementation):
Locate the parent folder id. Use the default from the DLFolderConstancts if you don't have any.
Assume the folder exists and try to get it.
It will throw you a NoSuch***Exception if not found. If this is the case, create the folder by hand
You could do something like this:
private Folder getOrCreateFolder(final ServiceContext serviceContext,
final long userId, final Group group, String folderName)
throws PortalException, SystemException {
final long parentFolderId = DLFolderConstants.DEFAULT_PARENT_FOLDER_ID;
final long repositoryId = group.getGroupId();
try {
final Folder prev = DLAppLocalServiceUtil.getFolder(
repositoryId, parentFolderId, folderName);
return prev;
} catch (final NoSuchFolderException e) {
final Folder newFolder = DLAppLocalServiceUtil.addFolder(userId,
repositoryId, parentFolderId, folderName,
"My cool new folder", serviceContext);
return newFolder;
}
}
The docs and stuff are absolutely leaky about why you call the addFolder() that way, take a look on the portal source. It's not that trivial but isn't that hard to get used to either.

How can we search a particular directory for files in C#?

Here i know the source folder path.But i want to search a particular folder like "MANAGERS" in the list of directories for files.Could we do this type of operation in C# Windows Application?Please help me regarding this.
You can use the DirectoryInfo class.
DirectoryInfo di = new DirectoryInfo(mySourceFolder);
DirectoryInfo[] diArr = di.GetDirectories();
foreach (DirectoryInfo dri in diArr)
{
if(dri.Name.ToUpperInvariant() == "MANAGERS")
{
FileInfo[] fiArr = di.GetFiles(); // get a list of files in directory
}
}

Create a directory on UNC Path web part sharepoint

I have created a web part which renders a button, on click of this button I want to access the directory of the other machine in LAN. Once I get the access to this Directory I will create a nested directories inside it with different extensions of files, but the problem is when I tries to access this folder by UNC Path it is giving me error like "Could not find a part of the path '\comp01\ibc'". Here comp01 is the computer name which is situated in LAN and ibc is a shared folder on that machine.
Following is the code for button click,
void _btnBackup_Click(object sender, EventArgs e)
{
try
{
//UNC Path --> \\In-Wai-Svr2\IBC
if (!string.IsNullOrEmpty(UncPath))
{
SPSite currentSite = SPControl.GetContextSite(this.Context);
SPWeb parentWeb = currentSite.OpenWeb();
string dir = Path.GetDirectoryName(UncPath);
//If IBC folder does not exist then create it.
if(!Directory.Exists(dir))
Directory.CreateDirectory(dir);
IterateThroughChildren(parentWeb, UncPath);
}
else
{
_lblMessage.Text = "UNC Path should not be empty";
}
}
catch(Exception ex)
{
_lblMessage.Text = ex.Message;
}
}
For UNC paths you need to specify it like this:
either use a C# string literal
String path = #"\\comp01\ibc";
or escape the string like
String path = "\\\\comp01\\ibc"
Try that.

Resources