MVC download images from ftp and show in VIew - asp.net-mvc

Have some pictures on ftp location. My controller is getting list of paths for some specific images placed on ftp. What i want to do is to use those paths to download those pictures to local temporary folder and then show them inside gallery in view. Currently i am struggling with model to download those pictures but have some problems when trying to download pictures. Error posted below as well as current code. There is also folder creation code missing.
This is my controller method which would get paths list then calling download method to download pictures from ftp location to some temporary folder (and this temporary folder should be besides my application that then view could open images from that folder:
Function Details(Optional ByVal id As Long = Nothing) As ActionResult
'--Temporary directory for pictures to be downloaded from ftp location (temp_dir) should be created besides application folders
Dim temp_dir As String = "/temp_dir/"
'--If not temp_dir exist ==> create this folder
'--if folder has been created properly go all next lines..
'--Take list of all ftp paths e.g \someFolderForPictures\image1.jpg to be downloaded to temp_dir
Dim PicsTrans As List(Of tblTransPics) = db.tblTransPics.Where(Function(f) f.IdTrans = id).ToList
'--For each picture path download it to temp_dir folder with temporary name
For Each imgFtpPath In PicsTrans
Dim temp_picName As String = Guid.NewGuid.ToString
DownloadFile(imgFtpPath.PicturePath, temp_dir & temp_picName)
Next
'-- If everythings went well - pass either temp_dir path to view and inside view those pictures will be opened or pass list of pictures (bytes)???
Return View(temp_dir)
End Function
Download file method:
Public Function DownloadFile(ByVal ftpPicLocation As String, destinationLocation As String) As Boolean
Dim reqFTP As FtpWebRequest
Try
reqFTP = DirectCast(FtpWebRequest.Create("ftp://someftpserver.com" & ftpPicLocation), FtpWebRequest)
reqFTP.Method = WebRequestMethods.Ftp.DownloadFile
reqFTP.UseBinary = True
reqFTP.Credentials = New NetworkCredential("myusername", "somepassword")
Using outputStream As New FileStream(destinationLocation, FileMode.OpenOrCreate)
Using response As FtpWebResponse = DirectCast(reqFTP.GetResponse(), FtpWebResponse)
Using ftpStream As Stream = response.GetResponseStream()
Dim bufferSize As Integer = 2048
Dim readCount As Integer
Dim buffer As Byte() = New Byte(bufferSize - 1) {}
readCount = ftpStream.Read(buffer, 0, bufferSize)
While readCount > 0
outputStream.Write(buffer, 0, readCount)
readCount = ftpStream.Read(buffer, 0, bufferSize)
End While
End Using
End Using
End Using
Return True
Catch ex As Exception
Throw New Exception("Failed to download", ex.InnerException)
End Try
End Function
the error occurs on this line:
Using outputStream As New FileStream(destinationLocation, FileMode.OpenOrCreate)
and it says:
Cannot find part of path „C:\temp_dir\f0f43089-4a16-4229-8ea6-2c3a55fde2ae”.
By the way how there could be C:\ ?

Remove first slash in your temp_dir variable.
Dim temp_dir As String = "temp_dir/"
With this slash it means you want to write into your root. Your root equals C:\
By removing the first slash you get your temporary folder under the folder your application is running.

Related

Hyperlinking a folder stored on iManage

I'm looking for a way to create a hyperlink to a particular folder in Worksite.
So far, I've only come up with a macro linking files on the basis of their database numbers but folders do not have database numbers (I think).
Another thing is that I wanted the folders to be opened in Outlook (Worksite is connected with Outlook and we access folders through it)
What I try to accomplish is creating hyperlinks in Excel for easy folder access (just like hyperlinks to files).
Does anybody have a clue if it's even possible? If yes, I'd appreciate an example of a code for this.
Thanks in advance.
Yes it's possible.
You don't mention which version of the iManage client you're working with however I'm going to assume FileSite 9.x. Installed with that client is a custom protocol handler which supports a custom URI scheme.
In effect this allows you to compose a hyperlink with plain text which you can then embed in your web page, or just start a new process in Windows to let the default browser load it up.
The custom protocol handler will parse it and then start up whatever iManage client it can (FileSite in your case) and then navigate to the correct folder.
Format is iwl:dms=[ServerName]&&lib=[DatabaseName]&&page=[FolderID]
Here's some C# that builds out such a string
var serverName = "MYSERVERNAME";
var databaseName = "MYDBNAME";
var serverName = "1234"; // internal numeric ID of folder (MHGROUP.PROJECTS.PRJ_ID in database, or IManFolder.FolderID via iManage COM API object model
var sb = new StringBuilder("iwl:");
sb.Append($"dms={serverName}");
sb.Append("&&");
sb.Append($"lib={databaseName}");
sb.Append("&&");
sb.Append($"page={serverName}");
// sb.ToString() will now output the hyperlink reference to your folder which you can pass to your web browser..
Sub Folder_link
Dim dmsIM As IManDMS
Dim dmsS As IManSession
Dim dmsD As IManDatabase
Dim FdR As IManFolder
Dim FdrLoc As String
Dim FdrID As Long
Const ServerName As String = <DMS name>
Const DatabaseName As String = <DatabaseName>
FdrLoc = "\\{DMS name}\{DatabaseName}\Main Folder\SubFolder\SubSubFolder\TargetFolderName"
Set dmsIM = New ManDMS
Set dmsS = dmsIM.Sessions.Add(ServerName)
dmsS.TrustedLogin
Set dmsD = dmsS.Databases.ItemByName(DatabaseName)
Set Fdr = Imanage.ImanFolder.Location (FdrLoc)
FdrID = Fdr.FolderID
With ThisWorkBook.WorkSheets(1).Range("A1")
.Hyperlinks.Add _
Anchor:=Selection, _
Address:="iwl:dms={serverName}&&lib={databaseName}&&page=" & FdrID, _
TextToDisplay:="link"
End With
End Sub

Create and download word file from template in MVC

I have kept a word document (.docx) in one of the project folders which I want to use as a template.
This template contains custom header and footer lines for user. I want to facilitate user to download his own data in word format. For this, I want to write a function which will accept user data and referring the template it will create a new word file replacing the place-holders in the template and then return the new file for download (without saving it to server). That means the template needs to be intact as template.
Following is what I am trying. I was able to replace the placeholder. However, I am not aware of how to give the created content as downloadable file to user. I do not want to save the new content again in the server as another word file.
public void GenerateWord(string userData)
{
string templateDoc = HttpContext.Current.Server.MapPath("~/App_Data/Template.docx");
// Open the new Package
Package pkg = Package.Open(templateDoc, FileMode.Open, FileAccess.ReadWrite);
// Specify the URI of the part to be read
Uri uri = new Uri("/word/document.xml", UriKind.Relative);
PackagePart part = pkg.GetPart(uri);
XmlDocument xmlMainXMLDoc = new XmlDocument();
xmlMainXMLDoc.Load(part.GetStream(FileMode.Open, FileAccess.Read));
xmlMainXMLDoc.InnerXml = ReplacePlaceHoldersInTemplate(userData, xmlMainXMLDoc.InnerXml);
// Open the stream to write document
StreamWriter partWrt = new StreamWriter(part.GetStream(FileMode.Open, FileAccess.Write));
xmlMainXMLDoc.Save(partWrt);
partWrt.Flush();
partWrt.Close();
pkg.Close();
}
private string ReplacePlaceHoldersInTemplate(string toReplace, string templateBody)
{
templateBody = templateBody.Replace("#myPlaceHolder#", toReplace);
return templateBody;
}
I believe that the below line is saving the contents in the template file itself, which I don't want.
xmlMainXMLDoc.Save(partWrt);
How should I modify this code which can return the new content as downloadable word file to user?
I found the solution Here!
This code allows me to read the template file and modify it as I want and then to send response as downloadable attachment.

.Net Charting access image generated in another session

I have a requirement where I need to access a chart generated in one session, in another.
To explain, process A generates some HTML which includes a chart with image url /ChartImg.axd?i=chart_0_0.png&g=a40f233f40fb4995b737d284f83ab1b7
I have deleteAfterServicing=false and dir=c:\, and if I look in c:\ chart_0_0.png is there.
Now process B (therefore running in its own session) comes along an opens the HTML file, the chart 404s because (it seems) the image handler will only allow access to that chart from the session it was created in.
Is there any way to disable this behaviour?
I look forward to your response
Karl
Ok so I solved it by doing the following:
Public Overrides Sub RenderControl(writer As System.Web.UI.HtmlTextWriter)
If Me.RenderToFile Then
'Save it to a file first
Me.SaveImage(HttpContext.Current.Server.MapPath(RenderToFileLocation),
ChartImageFormat.Png)
'Return the image urn
writer.Write("<img src=""" & Url.Content(ConfigurationManager.AppSettings("ChartFilePath")) & "?c=" & Url.Content(RenderToFileLocation) & """ />")
Else
MyBase.RenderControl(writer)
End If
End Sub
Then from there a created a simple .net MVC handler which returned the file and deleted it
Function Index(ByVal c As String) As ActionResult
Dim dir = Server.MapPath(ConfigurationManager.AppSettings("ChartFilePath"))
Dim filepath = System.IO.Path.Combine(dir, c)
Index = MyBase.File(filepath, "image/png")
'Delete the file
Try
IO.File.Delete(filepath)
Catch ex As Exception
End Try
End Function

How do I pull the URL/Path of the sharepoint document library I'm in from Excel VB?

I would like to set the filename for an item I create in an Excel Document Library. Howeverm when I try to interfere with the standard save with my own filename, it wants to save to my LOCAL MACHINE. I would happily like to supply the PATH if that is necessary, but I really DONT WANT TO HARD CODE IT.
Are there any properties I can use to parse this info? Meta data? Template?
Private Sub Workbook_BeforeSave(ByVal SaveAsUI As Boolean, Cancel As Boolean)
If SaveAsUI Then
Sheets("Purchase Order").Range("Description,VendorInfo,QUANTITY1,PRODUCT1,ITEM1,PRICE1,submitter,ShipVia,Terms,MACRO_ALERT").Interior.ColorIndex = xlColorIndexNone
Sheets("Purchase Order").Range("Location").Interior.Color = RGB(184, 204, 228)
Sheets("Purchase Order").Range("MACRO_ALERT").Value = ""
Dim MyFileName As String
Dim MyFilePath As String
' MyFilePath = "http://server/dept/purchasetracking/"
MyFilePath = Application.Path
MyFileName = "PO_" & Format(Now(), "yyyymmdd-hhnnss")
MsgBox (MyFilePath & MyFileName)
ActiveWorkbook.SaveAs Filename:=MyFilePath & MyFileName ', FileFormat:=52
' ActiveWorkbook.SaveAs Filename:=MyFileName
End If
End Sub
I like to use function GetSetting() and statement SaveSetting to save such informations to the registry (last used path, etc.).
When the file is opened from a SHP folder, ActiveWorkbook.Path starts with "http://". In this case you could save this path from a Sub Workbook_Open() procedure into the registry to retain the SHP path information. This can be later on used to offer a good path/filename to the user.
Hope that helps .... Good Luck MikeD

How do I create an empty MDB from ADO

I need to create an empty .mdb file, so that I can then run ADO commands on it (not ADO.NET). Is there a way to create an empty mdb using ADO?
Here are some code snippets that work:
string sADOProvider = "Provider=Microsoft.Jet.OLEDB.4.0;Data Source=";
ADOX.CatalogClass cat = new ADOX.CatalogClass();
string sCreate = MainForm.sADOProvider + sFullPath;
cat.Create(sCreate);
// The point of this code is to unlock the access file after we
// create it. You can tell it is unlocked if the .ldb file disappears.
System.Runtime.InteropServices.Marshal.ReleaseComObject(cat);
cat = null;
GC.Collect();
Not sure about creating it directly via ADO, but if Access is installed on the machine you could use Access to create the file via COM.
below is an early and late bound example. Both methods have their advantages / disadvantages.
Option Explicit
Sub CreateMDBEarlyBound()
'' Remember to set your reference to "Microsoft Access XX.0 Object Library"
Dim acApp As Access.Application
Set acApp = New Access.Application
acApp.NewCurrentDatabase ("c:\temp\MyDB-early.mdb")
Set acApp = Nothing
End Sub
Sub CreateMDBLateBound()
Dim acApp As Object
On Error Resume Next
Set acApp = GetObject(, "Access.Application")
On Error GoTo 0 '' turn off the resume next
If acApp Is Nothing Then
Set acApp = CreateObject("Access.Application")
End If
acApp.NewCurrentDatabase "c:\temp\MyDB-late.mdb"
Set acApp = Nothing
End Sub
In case "not ADO.NET" implies "not .NET", here's Corey Trager's code re-written as VBA:
Const sADOProvider As String = "Provider=Microsoft.Jet.OLEDB.4.0;Data Source="
Const sFullPath As String = "C:\DeleteMe.mdb"
Dim cat As ADOX.Catalog
Set cat = New ADOX.Catalog
Dim sCreate As String
sCreate = sADOProvider & sFullPath
cat.Create sCreate
' The point of this code is to unlock the access file after we
' create it. You can tell it is unlocked if the .ldb file disappears.
Set cat.ActiveConnection = Nothing

Resources