var fileStream = new FileStream(f, FileMode.Open);
newImage.SetValue("umbracoFile", fileStream); // causing a crash
_mediaService.Save(newImage);
Console.WriteLine(newImage.Name);
}
As you can see, I have tried both MemoryStream and FileStream. SetValue only takes two arguments (not three). I know I have access to MediaServices because in an earlier part of the program I was able to create a folder and a child folder with no problems. The line with the SetValue staement always crashes with the above exception.
I am a little frustrated to see no reply to my post, so perhaps I phrased it inaccurately. Since yestaerday, I have looked at the code on GitHub and reaised
a) there is absolutely no overload of Media.SetValue or ContentBase.SetValue that takes three arguments. So I can't use newImage.SetValue(alias,filename, stream)
b) The only overload of media.setvalue that can use a stream expects HttpPostedFile (Base)
I have tried an older solution from StackOverflow http://stackoverflow.com/questions/18636764/umbraco-mediaservice-umbraco-mediaitem-not-saving. This used a class which inherits from HttpPostedFileBase. Well it doesn't crash and it does allow me to create a media node in my Umbraco website. Sadly, the file itself is not posted properly and is given a url of http://localhost:54495/media/1003/20130524_085516.jpg. This does not exist. The crucial (I think) part of the derived class is the InputStream and looks like this return _fileInfo.OpenRead(); Basically I have followed all the instructions to the letter. The Umbraco folder I wanted is found, the file is found and an image node is created with the correct size, width and length. Just no image.
I have a really huge lot of images to upload to my website (40,000) and the Desktop Media Uploader cannot cope. I do not want to do them all by hand but after so many days of banging my head on this problem it is only stubbornness that keep s me going.
I think this should be easy. So what have I missed? Would be grateful for any help.
The method overloads you are looking for are actually extension methods for IContentBase which should become available to you by referencing the namespace:
using Umbraco.Core.Models;
I also noticed you have a Console.WriteLine() statement in your code snippet, does this mean you are uploading the files from a Console application? If that is the case you may want to reconsider as the content services require a web context (unless you are able to setup the context using Morten's approach)
Here's also an example using a surface controller which works for me in 7.2.4:
public class FileSurfaceController : SurfaceController
{
public ActionResult Index()
{
var filePath = @"C:\MyImage.jpg";
var file = new FileStream(filePath, FileMode.Open);
var parent = Services.MediaService.GetRootMedia().Single();
var media = Services.MediaService.CreateMedia("File1", parent, "Image");
media.SetValue("umbracoFile", Path.GetFileName(filePath), file);
Services.MediaService.Save(media);
return PartialView("File");
}
}
I am using Morten's approach (if I were not, then I would not be able to access any media folders or create any media. I have also looked through all the IContentBase extension methods. The ones for files all expect some variant of HttpPostedFile. Thank you very much for the example but I don't think I can use a Surface Controller as I am trying to stuff several thousand legacy images into a new website via a console application.
I am still utterlybaffled as to why I don't have any access to a version of SetValue which has three arguments. I can't even compile media.SetValue with three arguments. Perhaps that is the core issue.
Hmm. I have been wondering if I was just in the wrong overload. I feel sure that pretending to use an HttpPostedFile is non-ideal. I'll try putting in a using and get back to you poss Monday. Problem is, once I start baningn my head against that table it takes hours.
Just saw the overload. And it has three arguments. Hooray! Yes, I shall try this.
Um, that would be Umbraco.Core.Models. Yep. SO tempted to try it now but must get out to my garden. Thank you
Media/1004 does not exist as a folder and in any case the image should surely have been saved to a folder called "27353", which is the id of the new image. In fact, no new image has been added to the media folder in the website. This is very strange.
Just searched for the filename and discovered that the file has been saved in my console project under bin/Debug/media/1004. This is what the database object is looking for, though in the wrong place. I'll investigate this.
It looks like the console app has successfully created the media item in the database so I'm guessing you can just move the files from the debug folder to the website media folder and all should be fine? :)
OMG.. Thank you Lennart.. You're solution worked a treat! Have spent hours trying to figure this out as all I could find was solutions for HTTPPostedFile which is not what I wanted (I already had the file on the server HDD in a folder)..
Adding in the
usingUmbraco.Core.Models;
Then allowed me to use the overloaded method for "SetValue" which took the "umbracoFile", Filename and then the stream..
It saved the file into the Media folder on the server and added it all into the CMS as required..,
Unable to save an image into a media file via mediaservice
I refer to thread
https://our.umbraco.org/forum/developers/api-questions/54306-Media-service-SetValue-Problem?p=0#comment216183
which is helpful but possibly out of date. I am using version 7.2.4 (and also tried it with 7.7.7). Here is my code
foreach (var f in fileInfo)
{
var name = Path.GetFileName(f);
var newImage = _mediaService.CreateMedia(name, gallery, "Image");
//var buffer = File.ReadAllBytes(Path.GetFullPath(f));
//var strm = new MemoryStream(buffer);
var fileStream = new FileStream(f, FileMode.Open);
newImage.SetValue("umbracoFile", fileStream); // causing a crash
_mediaService.Save(newImage);
Console.WriteLine(newImage.Name);
}
As you can see, I have tried both MemoryStream and FileStream. SetValue only takes two arguments (not three). I know I have access to MediaServices because in an earlier part of the program I was able to create a folder and a child folder with no problems. The line with the SetValue staement always crashes with the above exception.
I am a little frustrated to see no reply to my post, so perhaps I phrased it inaccurately. Since yestaerday, I have looked at the code on GitHub and reaised
a) there is absolutely no overload of Media.SetValue or ContentBase.SetValue that takes three arguments. So I can't use newImage.SetValue(alias,filename, stream)
b) The only overload of media.setvalue that can use a stream expects HttpPostedFile (Base)
I have tried an older solution from StackOverflow http://stackoverflow.com/questions/18636764/umbraco-mediaservice-umbraco-mediaitem-not-saving. This used a class which inherits from HttpPostedFileBase. Well it doesn't crash and it does allow me to create a media node in my Umbraco website. Sadly, the file itself is not posted properly and is given a url of http://localhost:54495/media/1003/20130524_085516.jpg. This does not exist. The crucial (I think) part of the derived class is the InputStream and looks like this return _fileInfo.OpenRead(); Basically I have followed all the instructions to the letter. The Umbraco folder I wanted is found, the file is found and an image node is created with the correct size, width and length. Just no image.
I have a really huge lot of images to upload to my website (40,000) and the Desktop Media Uploader cannot cope. I do not want to do them all by hand but after so many days of banging my head on this problem it is only stubbornness that keep s me going.
I think this should be easy. So what have I missed? Would be grateful for any help.
Hi Amanda,
The method overloads you are looking for are actually extension methods for IContentBase which should become available to you by referencing the namespace:
I also noticed you have a Console.WriteLine() statement in your code snippet, does this mean you are uploading the files from a Console application? If that is the case you may want to reconsider as the content services require a web context (unless you are able to setup the context using Morten's approach)
Here's also an example using a surface controller which works for me in 7.2.4:
Grtz
L
Hi Lennart and thanks for your reply.
I am using Morten's approach (if I were not, then I would not be able to access any media folders or create any media. I have also looked through all the IContentBase extension methods. The ones for files all expect some variant of HttpPostedFile. Thank you very much for the example but I don't think I can use a Surface Controller as I am trying to stuff several thousand legacy images into a new website via a console application.
I am still utterlybaffled as to why I don't have any access to a version of SetValue which has three arguments. I can't even compile media.SetValue with three arguments. Perhaps that is the core issue.
The ContentExtensions in 7.2.4 do have an overload which takes a stream as an argument. Check line 487.
So have you tried adding the using directive in the top of your code file? It is crucial to bring them into scope (much like System.Linq)
Hmm. I have been wondering if I was just in the wrong overload. I feel sure that pretending to use an HttpPostedFile is non-ideal. I'll try putting in a using and get back to you poss Monday. Problem is, once I start baningn my head against that table it takes hours.
Just saw the overload. And it has three arguments. Hooray! Yes, I shall try this.
Um, that would be Umbraco.Core.Models. Yep. SO tempted to try it now but must get out to my garden. Thank you
Amanda
Hi Lennart,
I really thought that would do it! I hav eincluded Umbraco.Core.Models. This is my example code:
private static void TryAddImageToUmbraco(ApplicationContext context)
{
const string path = @"C:\Users\amanda\Dropbox\Photos\20130524_085516.jpg";
var file = new FileStream(path, FileMode.Open);
var service = context.Services.MediaService;
var testFolder = service.GetById(27348);
var newImage = context.Services.MediaService.CreateMedia(Path.GetFileName(path), testFolder, Constants.Conventions.MediaTypes.Image);
newImage.SetValue(Constants.Conventions.Media.File, Path.GetFileName(path),file);
service.Save(newImage);
}
Here is what I see in my media dashboard:
Media/1004 does not exist as a folder and in any case the image should surely have been saved to a folder called "27353", which is the id of the new image. In fact, no new image has been added to the media folder in the website. This is very strange.
Just searched for the filename and discovered that the file has been saved in my console project under bin/Debug/media/1004. This is what the database object is looking for, though in the wrong place. I'll investigate this.
Hi Amanda,
It looks like the console app has successfully created the media item in the database so I'm guessing you can just move the files from the debug folder to the website media folder and all should be fine? :)
Grtz
L
http://www.proworks.com/blog/2013/07/31/how-to-redirect-the-umbraco-media-path-to-another-location/
This was the solution. Thanks very much for your guidance!
OMG.. Thank you Lennart.. You're solution worked a treat! Have spent hours trying to figure this out as all I could find was solutions for HTTPPostedFile which is not what I wanted (I already had the file on the server HDD in a folder)..
Adding in the
Then allowed me to use the overloaded method for "SetValue" which took the "umbracoFile", Filename and then the stream..
It saved the file into the Media folder on the server and added it all into the CMS as required..,
Thank you so much!
Cheers Nathan, glad to hear that works for you :)
is working on a reply...