Copied to clipboard

Flag this post as spam?

This post will be reported to the moderators as potential spam to be looked at


  • Damian Green 452 posts 1433 karma points
    Feb 19, 2013 @ 13:36
    Damian Green
    0

    How do you Save/Upload a file to Media using the new MediaService API

    Looking at the API docs it says:

    It is worth noting that it is also possible to pass a HttpPostedFile, HttpPostedFileBase or HttpPostedFileWrapper to the SetValue method, so it can be used for uploads.

    Thats all good and well but looking through other docs all those objects are based around an actual HTTP post and to create those manually is a major ballache.

    Is it not possible to open a file, read it into a memory stream and then save it to a byte array and pass in somehow? I have tried this and it doesnt like the array as the SetValue is wanting (string,string).

    Here is what i have (ms is the media service)

    IMedia newDoc = ms.CreateMedia(doc.Text, folder, "File");
    
    string aName = string.Concat(ASSET_PATH, asset.AssetPath);
    
    MemoryStream uploadFile = new MemoryStream();
    using (FileStream fs = System.IO.File.OpenRead(aName))
    {
      fs.CopyTo(uploadFile);
    }
    
    newDoc.SetValue("umbracoFile", uploadFile.ToArray());  
    ms.Save(newDoc);

     

  • Damian Green 452 posts 1433 karma points
    Feb 21, 2013 @ 11:59
    Damian Green
    2

    Got a little futher with this but the API is now throwing an error. Maybe a bug?

    I have created a MemoryFile class which inherits from HttpPostedFileBase and all the relevant methods are overwridden etc but when I pass it to the API SetValue method it pukes.

    Here is the MemoryFile class:

    internal class MemoryFile : HttpPostedFileBase
        {
            Stream stream;
            string contentType;
            string fileName;
    
            public MemoryFile(Stream stream, string contentType, string fileName)
            {
                this.stream = stream;
                this.contentType = contentType;
                this.fileName = fileName;
            }
    
            public override int ContentLength
            {
                get { return (int)stream.Length; }
            }
    
            public override string ContentType
            {
                get { return contentType; }
            }
    
            public override string FileName
            {
                get { return fileName; }
            }
    
            public override Stream InputStream
            {
                get { return stream; }
            }
    
            public override void SaveAs(string filename)
            {
                using (var file = File.Open(filename, FileMode.CreateNew))
                    stream.CopyTo(file);
            }
    
        }

    and here is the code i now have adding to the umbracoFile property - passing in the MemoryFile (also tried the base class as shown below)

    IMedia newDoc = ms.CreateMedia(doc.Text, folder, "File");
    
    string aName = string.Concat(ASSET_PATH, asset.AssetPath);
    
    MemoryStream uploadFile = new MemoryStream();
    
    using (FileStream fs = System.IO.File.OpenRead(aName))
    {
      fs.CopyTo(uploadFile);
    }
    
    HttpPostedFileBase mf = new MemoryFile(uploadFile, "application/pdf", Path.GetFileName(aName));                            
    newDoc.SetValue("umbracoFile", mf); 

    The error thrown in object reference not set with the following stack trace:

    [NullReferenceException: Object reference not set to an instance of an object.]
       Umbraco.Core.Models.ContentBase.SetValueOnProperty(String propertyTypeAlias, Object value) +189
       Umbraco.Core.Models.ContentBase.SetPropertyValue(String propertyTypeAlias, String value) +8
       CallSite.Target(Closure , CallSite , Object , String , Object ) +169
       System.Dynamic.UpdateDelegates.UpdateAndExecuteVoid3(CallSite site, T0 arg0, T1 arg1, T2 arg2) +4053245
       CallSite.Target(Closure , CallSite , Object , String , Object ) +244
       Umbraco.Core.Models.ContentBase.SetValue(String propertyTypeAlias, Object value) +243
       Umbraco.Core.Models.ContentExtensions.SetPropertyValue(IContentBase content, XmlNode uploadFieldConfigNode, String propertyAlias, String propertyValue) +102
       Umbraco.Core.Models.ContentExtensions.SetFileOnContent(IContentBase content, String propertyTypeAlias, String name, Stream fileStream) +1373
       Umbraco.Core.Models.ContentExtensions.SetValue(IContentBase content, String propertyTypeAlias, HttpPostedFileBase value) +183
       Umbraco.Core.Models.ContentBase.SetPropertyValue(String propertyTypeAlias, HttpPostedFileBase value) +9

    However when i debug the memory file it is fully set - it is an object, the stream and fileame and content type etc are all set. Looks a valid object to me.  Only thinigs that dont have anything set are the timeout values on the stream but cant see this would be an issue when its a memory stream?

    In the stack trace seem to indicate it going off and saving some dynamic types.  Ive had a poke around the source but but sure whats going on.

    Any ideas anyone?

     

  • James Borza 34 posts 95 karma points
    Feb 21, 2013 @ 22:28
    James Borza
    0

    I've tried creating the HttpPostedFile manually and I'm getting the following when invoking the SetValue:

     

       at System.Web.HttpRawUploadedContent.CopyBytes(Int32 offset, Byte[] buffer, Int32 bufferOffset, Int32 length)

       at System.Web.HttpInputStream.Read(Byte[] buffer, Int32 offset, Int32 count)

       at System.IO.Stream.InternalCopyTo(Stream destination, Int32 bufferSize)

       at System.IO.Stream.CopyTo(Stream destination)

       at Umbraco.Core.IO.PhysicalFileSystem.AddFile(String path, Stream stream, Boolean overrideIfExists)

       at Umbraco.Core.IO.PhysicalFileSystem.AddFile(String path, Stream stream)

       at Umbraco.Core.IO.FileSystemWrapper.AddFile(String path, Stream stream)

       at Umbraco.Core.Models.ContentExtensions.SetFileOnContent(IContentBase content, String propertyTypeAlias, String name, Stream fileStream)

       at Umbraco.Core.Models.ContentExtensions.SetValue(IContentBase content, String propertyTypeAlias, HttpPostedFile value)

       at Umbraco.Core.Models.ContentBase.SetPropertyValue(String propertyTypeAlias, HttpPostedFile value)

       at CallSite.Target(Closure , CallSite , Object , String , Object )

       at Umbraco.Core.Models.ContentBase.SetValue(String propertyTypeAlias, Object value)

    Sigh, might have to just create the folder/save image/thumb manually for now.

     

  • Damian Green 452 posts 1433 karma points
    Feb 22, 2013 @ 09:59
    Damian Green
    0

    Thats what im thinking if we cant get it working in the next day or two.

    Shame because it borks the rest of my plans. :(

     

  • Damian Green 452 posts 1433 karma points
    Feb 22, 2013 @ 10:01
    Damian Green
    0

    What was the actual error you received? Thats is just the stack trace.

  • Damian Green 452 posts 1433 karma points
    Feb 22, 2013 @ 12:04
    Damian Green
    0

    I have raised this as an issue.

    If you are having a problem with this or can recreate please vote it up here and add any comments:

    http://issues.umbraco.org/issue/U4-1757

    Thanks

     

  • James Borza 34 posts 95 karma points
    Feb 23, 2013 @ 00:17
    James Borza
    0

    I got this working but changed my code so it actually uses a Post / HttpPostedFileBase. Only problem is the SetValue function seems to have a bug where the media properties Width and Height aren't set. It also doesn't create a folder properly, my new files are always placed in media/0/. I've given up on this method for now.

  • Damian Green 452 posts 1433 karma points
    Feb 25, 2013 @ 13:36
    Damian Green
    0

    Seems to be when uploading a FIle and not an Image so it may be the Height/Width issue that you reproduced.

     

  • Morten Christensen 596 posts 2773 karma points admin hq c-trib
    Feb 25, 2013 @ 14:09
    Morten Christensen
    100

    @James that issue has actually been fixed, so if you upgrade to latest nightly build the files will be placed in the correct folders and the height and width properties will also be set. The issue you are seeing is related to this fixed issue: http://issues.umbraco.org/issue/U4-1689

    http://nightly.umbraco.org/umbraco%206.0.1/UmbracoCms.6.0.1-build.29.zip

    As for the main issue in question I have added a comment here: http://issues.umbraco.org/issue/U4-1757#comment=67-5700

    - Morten

  • James Borza 34 posts 95 karma points
    Feb 25, 2013 @ 22:20
    James Borza
    0

    Thanks Morten.

  • Damian Green 452 posts 1433 karma points
    Feb 26, 2013 @ 10:53
    Damian Green
    0

    Issue now fixed in latest nightly build (30)

  • lj 81 posts 425 karma points
    Sep 13, 2013 @ 17:01
    lj
    0

    Dont know if any you can help with an issue I am having. I am creating a new media item using the method Damian has above. In my case I am creating an image. It seems to work fine and creates the media item which can be viewed in umbraco backend. The problem occurs when I view the image in the front end it does not appear.

    front end code I use is razor: dynamic mediaItem = new DynamicMedia(id);

    When I view this mediaItem in the debuger the niceurl value is not set. If i then go to the umbraco backend and view the media item and save when I then go back to the front end the image now displays and the niceurl field when viewed in the debuger is set.

    Is this a bug in the api or am i missing something here??? It seems the api is missing something out.

     

     

  • James Borza 34 posts 95 karma points
    Sep 13, 2013 @ 17:36
    James Borza
    0

    Try:

    mediaItem.GetPropertyValue("umbracoFile");

    or

    mediaItem.Url

    Not sure why the NiceUrl property isn't populated on save, it's most likely a bug.

  • lj 81 posts 425 karma points
    Sep 13, 2013 @ 17:57
    lj
    0

    James thanks for the reply.

    I think the problem has something to do with the fact im using a console app. just noticed the same thing is happening for pages I am creating using the content api with code I know worked when used from a web app. I think I maybe be missing a config setting possibly will look into it further.

Please Sign in or register to post replies

Write your reply to:

Draft