Sandboxing SourceFile.CopyFileTo(destination)

Some of my competitors in the Apple Store have apps that can save an entire folder to the desktop at the press of a button.

I am trying to do the same with SourceFile.CopyFileTo(destination) where destination = SpecialFolder.Desktop.

It works fine, but when I sandbox with App Wrapper Mini script, it simply does not do anything. I checked that FolderItem still pointed to the right folders.

Is SourceFile.CopyFileTo() impossible to achieve in a sandboxed application, and is there a possible workaround ?

Thanks is advance for any assistance.

I think the user has to select the destination folder through a SelectFolder Dialog to make it work when Sandboxed.
Or, there could be an entitlement to use.

If the user selects the desktop as the “default” save location, you can create a security-scoped bookmark and create a folder there anytime. You just need to resolve the bookmark and call StartAccessingSecurityScopedResource, create the folder/files/ then call StopAccessingSecurityScopedResource

https://developer.apple.com/library/mac/documentation/security/conceptual/AppSandboxDesignGuide/AppSandboxInDepth/AppSandboxInDepth.html#//apple_ref/doc/uid/TP40011183-CH3-SW16

[quote=39533:@Albin Kiland]I think the user has to select the destination folder through a SelectFolder Dialog to make it work when Sandboxed.
Or, there could be an entitlement to use.[/quote]

The SelectFolder works, but then CreateAsFolder does not.

You got me completely lost. How am I supposed to do this in Xojo ?

You could do it with declares… I use the MBS plugins and they work very well for this. I think MacOSLib has the needed calls also. Not 100% sure about that though.

If I were you, I would communicate with Sam Rowland of Ohanaware http://www.ohanaware.com/
He has done extensive work with Security Scoped Bookmarks and has always been forthcoming with advice when I asked.

Here’s a simple example using MacOSLib

To create a bookmark that can be saved in your app’s preferences-

[code] dim f As FolderItem=SelectFolder
dim bookmark As String
dim myNSURL As new NSURL(f)
dim options As integer=NSURL.NSURLBookmarkCreationMinimalBookmark

'for sandboxed app would be
'options=options+NSURL.NSURLBookmarkCreationWithSecurityScope
'if read only access is required
'options=options+NSURL.NSURLBookmarkCreationSecurityScopeAllowOnlyReadAccess

bookmark=EncodeBase64(myNSURL.BookmarkData(options,array(""),nil).StringValue)

TextArea1.text=bookmark[/code]

To resolve a bookmark-

[code] dim f As FolderItem
dim bookmark As String=DecodeBase64(TextArea1.Text)
dim options As integer=0
'for sandboxed app would be
'options=NSURL.NSURLBookmarkResolutionWithSecurityScope

dim myNSURL As new NSURL(new NSData(bookmark),options,nil,false)

MsgBox "Resolved to: "+myNSURL.FilePathURL.absoluteString[/code]

Then when you need to access the location to create files, etc…

[code]err=myNSURL.StartAccessingSecurityScopedResource

//do sutff with myNSURL.item

err=myNSURL.StopAccessingSecurityScopedResource[/code]

Of course you’ll need to add error/nil checking.
MBS plugins are almost an identical process, mostly just naming difs.

[quote=39624:@jim mckay]Here’s a simple example using MacOSLib

[/quote]

I appreciate your precise example, and shall now try and learn how to use MacOSLib.

Thank you.

[quote=39619:@Roger Clary]If I were you, I would communicate with Sam Rowland of Ohanaware http://www.ohanaware.com/
He has done extensive work with Security Scoped Bookmarks and has always been forthcoming with advice when I asked.[/quote]

Sam is knowledgeable and awfully gracious indeed. He was extremely helpful to help me understand how to apply declares. I just need to research more before seeking his help. At this stage, I am discovering much more than I had thought needed to go around sandboxing limitations. Guess I was lucky my first apps did not require too ambitious features ;

There could be several ways they’ve accomplished this.

If there is a way how I can download a version of their app (that is Sandboxed) I might be able to tell you how they’ve done this.

The main issue is that your application doesn’t have access to the Desktop folder as standard. Do you recall using a dialog to select the desktop folder? If not, then chances are they may have a TE (Temporary Entitlement). There is support for TEs in App Wrapper, check out the Specific locations section on the “Package” panel. However TEs come with a very BIG if. That is you can not guarantee your app will be approved with a TE. If a App Reviewer believes that your app shouldn’t have it, then it gets messy. I’ve seen too many people struggle with TEs, in getting the App Reviewer to approve their usage.

In general my advice is, only support Security-Scoped Bookmarks as a last resort. They are flaky, and even if you use them right, they can lead to a corrupted container, locking your application out of accessing any file on the system (including the app’s own resources).

If you do need to use SSB, make sure that it’s for the short period of time possible, i.e. if you app reads sections from a file, load the whole thin into memory, then reads the sections from there. If a SSB is open for too long (no time limit specified), the OS will close it for you. Causing a whole world of pain, especially on slower systems!

If you think you might need to use SSBs, feel free to ask first as there are other ways for some cases which don’t have any problems and in same cases require next to no code changes.

Also never use a app-SSB to load a document that contains document SSBs, while this does work, Apple actually advise against it and it can lead to issues.

Try not to open and close SSBs (which you need to do to get anything from the file). If you app displays file information in one place and contents in another, load it all and cache it.

The other thing to watch out for, is that you only have ONE access to a file at ONE time, technically you can have multiple access to one file, but this does also appear to cause issues.

Bookmarks that created with the non-Sandboxed version are not Security Scoped and will not work in a Sandboxed version of the application.

Oh and last but not least, if your app is used on 10.6, then the user upgrades to 10.7.3 or newer, none of the bookmarks are SSB. If you user has 10.7 ~ 10.7.2, SSBs won’t work and neither will regular bookmarks.

When I click on a button, a folder ops up on the desktop. I never had a chance to let tem know where I wanted the folder.

But I can certainly do it in a more proper way, and prompt the user for a place where to save the folder. Given the hurdle, here is what I am considering :

  • As the user where to save
  • Save a compressed file with a zip extension that contains the font files they purchased.

I did not have time to experiment today, but it seems that wen the user is prompted to save, saving a binary file is acceptable to the sandbox…

Somehow, I would like better to avoid risky things and stick with the simplest code as possible. My next app will have to save data files for users, and it best be plain Xojo if I can.

TE and Bookmark stories are scary :frowning:

[quote=39904:@Michel Bujardet]As the user where to save
Save a compressed file with a zip extension that contains the font files they purchased.
I did not have time to experiment today, but it seems that wen the user is prompted to save, saving a binary file is acceptable to the sandbox…

Somehow, I would like better to avoid risky things and stick with the simplest code as possible. My next app will have to save data files for users, and it best be plain Xojo if I can.[/quote]
That seems perfectly reasonable, and actually might be more appropriate for the end user, especially if they wanted to save it to a USB stick, they can do that from the Save as Dialog.

You can create any file, as long as it is the one that the user specifies in the dialog. For instance if they specify ~/Desktop/MyFile.zip, that is where you can save, you can’t rename the file, so you must also specify the filter with an explicit file extension for the save dialog.

I’m sorry if I scared you, I agree with the principle of Sandboxing, but we got bit bad some of the issues with SSBs (A seasonal product, that got locked out for some users)… It was embarrassing and frustrating. Since then, I’ve invested a lot of time trying to avoid these potential disasters. We have successfully used them in other apps since, but the first experience was the most painful.

As for TEs, Apple said they were only temporary and to avoid them unless you really needed them, but it’s down to the App Reviewer if you can actually use a TE or not. Some things will get a blanket NO, like using Apple Script to control Finder or System Events, but others can get a NO, simply because there’s an API equivalent. So, I’d stick to trying to avoid them. One day they’ll be gone anyway.

Sometimes, I sorta do a brain spew, where stuff comes out, relevant stuff mind you, but in a muddled order… I think this is one of those!

Argh… sandboxing … a coders nightmare. :slight_smile:

It’s allright. I actually enjoy exchanging ideas aloud, and appreciate very much your insight.

What I personally take from that is :

  • Keep learning API,
  • Leave TE alone because they are ground for arbitrary decisions upstairs

Altogether, I was very afraid of sandboxing before, then I bought App Wrapper Mini and found the process a lot easier (Thanks Thanks Thanks). What remains confusing is the lack of synthetic documentation that would say ‘Sandboxing compatible’ or ‘not SB compatible’ for given commands and classes in Xojo. We all seem to have to resort to trial and error.

From what I experimented so far about iOS and XCode, it maybe even be worse when Xojo mobile is here. Requirements in that environment seem even tougher.

Well ; if coding was too easy, selling software would become impossible anyhow :wink:

I just added to my latest app a button that says “Backup all fonts” and after a MsgBox explains what will happen, lets the user save a copy of a zip file I placed in the bundle. I works beautifully in the sandboxed version.

Power users will be satisfied to have that, and others will still have the clickable interface to install each font.

And no TE :slight_smile:

LOL! It’s certainly made developing software harder![quote=40051:@Michel Bujardet]I just added to my latest app a button that says “Backup all fonts” and after a MsgBox explains what will happen, lets the user save a copy of a zip file I placed in the bundle. I works beautifully in the sandboxed version.[/quote]
Excellent.

Too true.[quote=40004:@Michel Bujardet]From what I experimented so far about iOS and XCode, it maybe even be worse when Xojo mobile is here. Requirements in that environment seem even tougher.[/quote]
I guess we’ll have to wait and see, I’m hoping it will be easier as you can’t build an unsandboxed app for iOS.