How can I know or construct the permanent url to a given file - box-api

We have an internal application that owns the folders for a given topic; topic subscribers are added as collaborators via the api. When a message to the topic contains an attachment, we upload it to the folder, where is can be accessed by the topic subscribers via a link we show in the rendered message.
The problem we have is partially an organizational issue:
Our users are restricted to shared links of a maximum time frame
This application uses a generic account from which it shares out these files, but there's no way to exclude it from the policy of shared links expiration
Our idea was to get the file url (eg. https://acme.app.box.com/files/0/f/689840703/1/f_17027007623 ) and display that link instead of a shared collaboration. It's not obvious from the documentation how to do so ...

Assuming the URL format doesn't change, you can template it as:
https://acme.app.box.com/files/0/f/$FolderId/1/f_$FileId
$FolderId is already known to you because you're programmatically uploading files to that folder.
$FileId can be derived from the File object that's returned to you as a result of the upload.

Related

File.getResourceKey consistently returns null in Google Apps Script

According to a recent email from GoogleDevelopers, it will be necessary to specify a resourceKey when fetching some files and folders after the security update on the 13th of September 2021. They say "To avoid errors accessing files, you must update your code for accessing files to include the appropriate resource keys."
Fetching the key appears to work for folders:
var folder = DriveApp.getFolderById(folderId);
var folderResourceKey = folder.getResourceKey();
If I understand correctly, after the security update it will still be possible for the developer to use this method to fetch the resource key (assuming appropriate sharing settings on the folder). Then we can hardcode the resource key in the script for use in a getFolderByIdAndResourceKey call.
However, when I try this on a File instead of a Folder, I consistently receive "null" for the resource key:
var file = DriveApp.getFileById(fileId);
var resourceKey = file.getResourceKey();
I've tried this for several files, including files which I own and which I created months ago, so I don't think it can be an instance of this issue:
Unpredictable result of DriveId.getResourceId() in Google Drive Android API
The API documentation indicates that it should work the same way for Files as for Folders:
https://developers.google.com/apps-script/reference/drive/file?hl=en#getResourceKey()
https://developers.google.com/apps-script/reference/drive/folder?hl=en#getresourcekey
I also tried getTargetResourceKey in case the files were links, but the result was still null:
https://developers.google.com/apps-script/reference/drive/file?hl=en#gettargetresourcekey
After loading the file in the web browser, I tried clicking on "File -> Document details", but it doesn't show the metadata.
This API document indicates that the resource key is included when you fetch the metadata, but I think the context of this page is different and I can't see how to fetch this metadata from Google Apps Script:
https://developers.google.com/drive/api/v3/reference/files
Even if I can work out the context in which I can fetch that metadata, I don't have much hope that it's going to contain the resource key which is not provided by the GAS API.
Is there any way for the Google Apps Script developer to fetch the resource keys for files?
You can now use getSecurityUpdateEnabled announced on August 31, 2021:
Gets whether this File requires a resource key for access when it's shared using a link. This requirement is turned on by default for eligible files and folders. To turn the resource key requirement on or off for eligible files, use setSecurityUpdateEnabled.
Source: https://developers.google.com/apps-script/reference/drive/file#getsecurityupdateenabled
Use it to check if file requires resource key:
var file = DriveApp.getFileById(fileId);
if (file.getSecurityUpdateEnabled())
{
// resource key is required for the file
// ..
}
Announced methods include methods to get whether files/folders are eligible for security update:
File.getSecurityUpdateEligible() / Folder.getSecurityUpdateEligible()
Announced methods include methods to set whether files/folders require a resource key for access when they shared using a link:
File.setSecurityUpdateEnabled(enabled) / Folder.setSecurityUpdateEnabled(enabled)
General info on why files/folders may return null instead of resource key string:
From current documentation (bold is mine):
Access link-shared files using resource keys
A file that is shared with the link can only be discovered by users that can access the file as a result of a type=user or type=group permission. Requests from users that only have access to these link-shared files via a type=domain or type=anyone permission, may require a resource key.
This resource key requirement only applies to a subset of old files.
For more information about permissions, see Share files, folders and drives.
So, as far as I can tell, there is no indication that each Google Drive file should have non-null resource key, unless it's link-shared with specific permission, and somehow required only for subset of old files.

Can the OneNote API copy a notebook or section from one user to another user in Office 365

I'm trying to copy section of a notebook, or even notebook itself, from a notebook in one user's OneDrive to another user's notebook in their OneDrive. The user I'm logged in as has permissions to read and write both notebooks. I'm getting the error response:
message=The specified resource ID does not exist.
#api.url=http://aka.ms/onenote-errors#C20102
code=20102
Where the path I'm using is of the form https://www.onenote.com/api/v1.0/users/{id}/notes/sections/{id}/copyToNotebook where the ids in that are for the source section.
which is presumably because the id in the post request represents a notebook under a different user.
If I was copying to a SharePoint site or group then the post request can have additional ids to identify that, so it be logical if there was a argument to identify the user to copy to.
Copying works perfectly when both notebooks are within the same user's OneDrive.
Is there any way of doing it between users in Office 365 OneDrive?
Yes, you can copy a section from one notebook to another user's notebook, as long as you have write permission to that user's notebook (or a notebook under another site).
In you scenario, the destination/post body has to contain the ID to the notebook, as well as the siteCollectionId and siteId, or the groupId of the site where the notebook is stored. (Checkout the message body format here). If you want to copy the section to another user's notebook, you will need the siteCollectionId and siteId of that user's OneDrive for Business; if you want to copy it to a notebook stored in a site, you will need the IDs for that site.
The reason you need those extra IDs is because by default the copy API will consider the destination notebook is stored in your OneDrive for Business. By specifying those IDs you tell the API that the destination is in another location. I'm assuming you didn't provide those IDs that you got the error.
You get get more information about obtaining the siteCollectionId and siteId here.

Google Drive API permission propagation and the File userPermission property

I am not sure if I am experiencing bugs or if I am doing something wrong. I am developing an app that allows users to create and share a folder on their Google Drive so they can collaborate on the contents of the folder. The folder is created at the root of the user's Google Drive and initially contains a couple of files and one sub-folder with more files.
The first issue is that after inserting a new permission on the main folder, the permission will usually propagate down to all the files and sub-folders, but sometimes it fails to insert the permission on one of the files in the sub directory. Is this feature of propagating permissions to sub-directories something that is officially supported or am i suppose to insert a permission into all the files separately?
The second issue I am experiencing involves the use of the File's userPermission property to check if the role of the current user has changed. It seems that the userPermission property sometimes contains the permission of a recent user and not the current user. The feature I am trying to implement is the ability for a user with whom a folder was shared to check periodically if their permission role has changed. For example has the users permission role changed from "reader" to "writer" or vice-versa. This usually works by listing the folder with the fileId and checking the role property of the userPermission property of the file. However if I am testing this feature with both the user who shares and the user with whom it is shared working within the same client, the get file result will often list the userPermission as the last one to access the file and not the current user. I have tested if this was because I was using the wrong oauth information in the request header but I have ruled this possibility out, the oauth headers are correct for each separate call to get file. I added a test call to about witch lists the users permissionId, just before a call to get file to confirm who the authorized user is. Sill the userPermission with the "me" name appears for the wrong user.
The workaround I have found is to use list files which returns the file in the list with the correct userPermission.
In the reference located at https://developers.google.com/drive/v2/reference/files#resource for the description of the userPermission property is "The permissions for the authenticated user on this file."
I am wrong to interpret this to mean the userPermission will always show the role of the current user? And if it is showing the wrong permission, what could be the cause??
userPermission and me represents the current authenticated user, if it's showing the wrong permission you're authenticating the user with the wrong token.
the permission will usually propagate down to all the files and sub-folders
This case may not be true for sub folders and files with their own explicit permissions.
With regard to the first problem, which was that after sharing a folder, only one of its contents would consistently not get shared, I have discovered the cause. The file that was not getting shared is actually a Fusion Tables file and in my script, immediately after inserting the permission, a call is made to insert a new row into the Fusion table file which seems to prevent the permission from being added to that file at that time, or ever. So the workaround I found is to wait a couple of seconds after making the insert permission call, then check that the permission is already in place using a list permission call before calling the Fusion Tables query.
Now with regard to the second problem, this is probably a bug of some sort since I confirmed that I am using the correct oauth token, and by the fact that the workaround I have found works, which is to use a call to list file instead of get file. The only difference is that the file name or other query parameter is required to make the call in addition to the file id. In my case the file object returned with the list file will always contain the correct values in the userPermission field whereas with get file, the userPermission will sometimes contain information for an other user.

Transfer ownership for ALL files in user's google drive - using google-api-java-client and the Drive SDK

We have a google corporate account and need to transfer ALL of a user's google drive files to another account in certain instances. We want to do what is described at the following link for "all files" but programatically via the latest Drive API http://support.google.com/a/bin/answer.py?hl=en&answer=1247799
We are currently using the following API version(s) below, coupled with domain wide authority delegation as described at https://developers.google.com/drive/delegation and are able to see a user's files, iterate over them etc.
google-api-services-drive 1.14.2-beta
google-api-client 1.14.1-beta
My question is this: it appears that the only way to change permissions is by fileId by fileId etc. Instead of having to traverse and iterate over an entire set of user's files, if we just want to transfer ALL of a user's files to another particular user: is there a way in the API to do this (ownership transfer for ALL files) rather than individual requests file/by file?
Also when transferring ownershisp, must the transferee be in the same #domain or can it be another #domain we manage? I read somewhere that you can only transfer to owners in the same domain. Does this still hold true? For instance we manage #myCompany.com and have our corporate account registered under that, however that shell account has several sub-domains within it. We would like to transfer files from users in the sub-domains to a central user in the #myCompany domain.
You need to change permissions file by file, there is no updateAll type of functionality at the moment.
You cant transfer the ownership to another domain's user. Ownership can only be transferred to another user in the same domain as the current owner.
This answer doesn't directly answer your question, but it could be helpful for both you and future visitors.
As of now, you can mass transfer files to new users with Google's new Admin console. It doesn't let you filter for specific folders, but it does allow you to transfer all of one user's Drive files to a second user.
I know you were trying to create something which uses the API to iterate through folders and files, and you probably have a very specific use-case in mind. However, in the case where you have employees leaving, or you need to transfer everything, using the following method is fast and simple.
Open the Google Admin console
Go to Google Apps > Drive
Click on "Transfer ownership"
Fill out both user fields and submit
This process will even email both users once the process is completed.
You can do this with a single call to the Data Transfer API
Exactly what is needed but only with API!
Open the Google Admin console
Go to Google Apps > Drive
Click on "Transfer ownership"
Fill out both user fields and submit
This process will even email both users once the process is completed.
If this is not possible via API calls, then there is no point deleting a user using API.

Finding external shares using Google Drive

I currently have an application that will search document acls and report back on any external sharing. Since the deprecation of the document list api I would like to covert this application to Google Drive but since the user email address is no longer present in the Permission object returned from Drive is there any way to detect these shares?
Thanks.
Match the username you get from the Owner field to the users in your directory using the profile api https://developers.google.com/google-apps/profiles/. If the user is not in the directory, the user is external.
I suggest you to use 'domain' field in permission to define if your document is shared with an external user or not. You have to campare this field with the domain that you own.
Thanks,