How to update the content of a file in Google Drive? - java

I am trying to update the content of a Google Doc file with the content of another Google Doc file. The reason I don't use the copy method of the API is because that creates another file with another ID. My goal is to keep the current ID of the file. This is a code snippet which unfortunately does nothing:
com.google.api.services.drive.Drive.Files.Get getDraft = service.files().get(draftID);
File draft = driveManager.getFileBackoffExponential(getDraft);
com.google.api.services.drive.Drive.Files.Update updatePublished = service.files().update(publishedID, draft);
driveManager.updateFileBackoffExponential(updatePublished);
The two backoffExponential functions just launch the execute method on the object.
Googling around I found out that the update method offers another constructor:
public Update update(java.lang.String fileId, com.google.api.services.drive.model.File content, com.google.api.client.http.AbstractInputStreamContent mediaContent)
Thing is, I have no idea how to retrieve the mediaContent of a Google file such as a Google Doc.
The last resort could be a Google Apps Script but I'd rather avoid that since it's awfully slow and unreliable.
Thank you.
EDIT: I am using Drive API v3.

Try the Google Drive REST update.
Updates a file's metadata and/or content with patch semantics.
This method supports an /upload URI and accepts uploaded media with
the following characteristics:
Maximum file size: 5120GB Accepted Media MIME types: /*
To download a Google File in the format that's usable, you need to specify the mime-type. Since you're using Spreadsheets, you can try application/vnd.openxmlformats-officedocument.spreadsheetml.sheet. Link to Download files for more info.

Related

Uploading large file to SharePoint with metadata using Microsoft Graph SDK for java

Uploading a large file to SharePoint Online (Document library) via the MS Graph SDK (Java) works for me, but adding also metadata on an upload seems to be hard
I tried the to add the metadata inside the DriveItemUploadableProperties, because I didn't find any hints where the right place should be
DriveItemUploadableProperties value = new DriveItemUploadableProperties();
value.additionalDataManager().put("Client", new JsonPrimitive("Test ABC"));
var driveItemCreateUploadSessionParameterSet = DriveItemCreateUploadSessionParameterSet.newBuilder().withItem(value);
UploadSession uploadSession = graphClient.sites(SPValues.SITE_ID).lists(SPValues.LIST_ID).drive().root().itemWithPath(path).createUploadSession(driveItemCreateUploadSessionParameterSet.build()).buildRequest().post();
LargeFileUploadTask<DriveItem> largeFileUploadTask = new LargeFileUploadTask<>(uploadSession, graphClient, fileStream, streamSize, DriveItem.class);
LargeFileUploadResult<DriveItem> upload = largeFileUploadTask.upload(customConfig);
This results in a 400 : Bad Request response
How can I add metadata on an upload the right way?
AFAIK, you cannot add metadata while uploading to Sharepoint. You will have to make two separate requests, one to upload the file, and one to add additional metadata to the file that you just uploaded.
Before adding your own custom metadata, you must register the facets / schema to OneDrive. Refer to this doc :
https://learn.microsoft.com/en-us/onedrive/developer/rest-api/concepts/custom-metadata-facets?view=odsp-graph-online
But you should be aware that because custom facets are a feature in preview, at the time of this post you have to literally contact an MS email and get the custom facet manually approved, there is no automatic API to do this unfortunately.
If you somehow manage to get the custom facet approved :
DriveItemUploadableProperties has preset fields such as filename, size, etc. meant to represent the upload task and basic details about the file, there are no options to add additional metadata to it. Refer to the documentation for DriveItemUploadableProperties :
https://learn.microsoft.com/en-us/graph/api/resources/driveitemuploadableproperties?view=graph-rest-1.0
I assume that when you say, "Uploading a large file to SharePoint Online (Document library) via the MS Graph SDK (Java) works for me", you are able to successfully upload the file and obtain the item ID in the response from the uploaded file. You can use the item ID to update the metadata of the file via a second request. Specifically, refer to the update driveitem here :
https://learn.microsoft.com/en-us/graph/api/driveitem-update?view=graph-rest-1.0&tabs=http
GraphServiceClient graphClient = GraphServiceClient.builder().authenticationProvider( authProvider ).buildClient();
DriveItem driveItem = new DriveItem();
driveItem.name = "new-file-name.docx";
graphClient.me().drive().items("{item-id}")
.buildRequest()
.patch(driveItem);
Edit :
As additional information, you can use a ListItem rather than a DriveItem resource and input custom fields there. However, you should be aware that unlike custom facets that I mention above, custom metadata stored in these fields are not indexed and is not meant to be queried / filtered on large datasets, which is the most common use case for metadata. When querying for these fields you must include the
Prefer : HonorNonIndexedQueriesWarningMayFailRandomly
in the request header, and as the header says you should be aware that the query may fail randomly in large datasets.

Uploading File in DAM Programmatically using AssetManager? What MimeType should I use?

I have a form that uploads a File to a SlingServlet. The SlingSerlvet receives the file and it tries to save the file in DAM using com.day.cq.dam.api.AssetManager.(i.e. Save file in DAM programmatically)
The problem arises with MIME types. The user may upload a pdf,xls, doc etc. so the Type is not fixed. I don't know what to set the MIME type as(see the third parameter xxx) assetMgr.createAsset(newFile, is,"xxx", true);
I tried "application/octet-stream" but CQ ignores the Type saying asset ignored.
Log:
27.11.2014 18:58:48.595 *INFO* [JobHandler: /etc/workflow/instances/2014-11-27/model_879500607401687:/content/dam/videojetdocuments/videojetdocuments/offerletters/Präsentation_Dominik_Suess.pdf/jcr:content/renditions/original] com.day.cq.dam.video.FFMpegThumbnailProcess execute: asset [/content/dam/videojetdocuments/videojetdocuments/offerletters/Präsentation_Dominik_Suess.pdf] is not of a video mime type, asset ignored.
27.11.2014 18:58:48.596 *INFO* [JobHandler: /etc/workflow/instances/2014-11-27/model_879500607401687:/content/dam/videojetdocuments/videojetdocuments/offerletters/Präsentation_Dominik_Suess.pdf/jcr:content/renditions/original] com.day.cq.dam.video.FFMpegTranscodeProcess execute: asset [/content/dam/videojetdocuments/videojetdocuments/offerletters/Präsentation_Dominik_Suess.pdf] is not of a video mime type, asset ignored.
I tried this using the following link
Is there any generic MIME Type for such type of Files?
You can use the Apache Sling MimeTypeService to compute the mimetype based on an incoming filename. See also http://sling.apache.org/documentation/bundles/mime-type-support-commons-mime.html
If you don't have the filename you'll need something like the Apache Tika Detector, which analyzes the binary to try to guess its mimetype. I don't know if CQ provides such a service out of the box, but if it doesn't you could integrate it yourself.
Edit:
API that checks the MIMEType based on Magic headers Link
Helpful link for understanding the above mentioned problem Link

Extracting media objects present in LibreOffice Impress using LibreOffice APIs

I am trying to get details of the media contents (video, audio ) present in a LibreOffice Impress document through LibreOffice API in java. The details which I want to extract is the type of media content present in the document. And also ways to export them. I have gone through the java examples given on the Website but could not find anything relevant to type of video or audio present in file and extraction of video files. I have gone through the example given for exporting Images from Impress Documents using GraphicExportFilter, but it is not able to export video or audio files present in the document. I also tried to extract the type of media content by using XShape (code below), but it only gives the name of the media content and not its type(audio/video/or media extension).
For exporting I am also aware of the method of converting documents to pptx and then renaming and extracting all types of media files. But I suppose that would consume more time to extract (correct me if I am wrong) in practical application, so I was trying to do the same by LibreOffice API.
XComponent xDrawDoc = Helper.loadDocument( xOfficeContext,fileName, "_blank", 0, pPropValues );
XDrawPage xPage = PageHelper.getDrawPageByIndex( xDrawDoc,nPageIndex );
XIndexAccess xIndexAccess = UnoRuntime.queryInterface(XIndexAccess.class,xPage);
long shapeNumber = xIndexAccess.getCount();
for(int j=0;j < shapeNumber;j++)
{
XShape xShape =UnoRuntime.queryInterface(XShape.class, xPage.getByIndex(j));
XNamed xShapeNamed =UnoRuntime.queryInterface(XNamed.class, xShape);
System.out.println(j+":"+xShapeNamed.getName());
}
(This code gives me the names of the media contents present in Impress but not its type or extension)
Thanks in Advance..

Create Empty CloudBlockBlob in Azure

I'm hoping the answer to this question is quite simple, but I can't get it working after looking at the Azure Java API documentation.
I am trying to create an empty CloudBlockBlob, which will have blocks uploaded to it at a later point. I have successfully uploaded blocks before, when the blob is created upon the first block being uploaded, but I can't seem to get anything other than ("the specified blob does not exist") when I try to create a new blob without any data and then access it. I require this because in my service, a call is first made to create the new blob in Azure, and then later calls are used to upload blocks (at which point a check is made to see if the blob exists). Is it possible to create an empty blob in Azure, and upload data to it later? What have I missed?
I've not worked with Java SDK so I may be wrong but I tried creating an empty blob using C# code (storage client library 2.0) and if I upload an empty input stream an empty blob with zero byte size is created. I did something like the following:
CloudBlockBlob emptyBlob = blobContainer.GetBlockBlobReference("emptyblob.txt");
using (MemoryStream ms = new MemoryStream())
{
emptyBlob.UploadFromStream(ms);//Empty memory stream. Will create an empty blob.
}
I did look at Azure SDK for Java source code on Github here: https://github.com/WindowsAzure/azure-sdk-for-java/blob/master/microsoft-azure-api/src/main/java/com/microsoft/windowsazure/services/blob/client/CloudBlockBlob.java and found this "upload" function where you can specify an input stream. Try it out and see if it works for you.

Running a JavaScript command from MATLAB to fetch a PDF file

I'm currently writing some MATLAB code to interact with my company's internal reports database. So far I can access the HTML abstract page using code which looks like this:
import com.mathworks.mde.desk.*;
wb=com.mathworks.mde.webbrowser.WebBrowser.createBrowser;
wb.setCurrentLocation(ReportURL(8:end));
pause(1);
s={};
while isempty(s)
s=char(wb.getHtmlText);
pause(.1);
end
desk=MLDesktop.getInstance;
desk.removeClient(wb);
I can extract out various bits of information from the HTML text which ends up in the variable s, however the PDF of the report is accessed via what I believe is a JavaScript command (onClick="gotoFulltext('','[Report Number]')").
Any ideas as to how I execute this JavaScript command and get the contents of the PDF file into a MATLAB variable?
(MATLAB sits on top of Java, so I believe a Java solution would work...)
I think you should take a look at the JavaScript that is being called and see what the final request to the webserver looks like.
You can do this quite easily in Firefox using the FireBug plugin.
https://addons.mozilla.org/en-US/firefox/addon/1843
Once you have found the real server request then you can just request this URL or post to this URL instead of trying to run the JavaScript.
Once you have gotten the correct URL (a la the answer from pjp), your next problem is to "get the contents of the PDF file into a MATLAB variable". Whether or not this is possible may depend on what you mean by "contents"...
If you want to get the raw data in the PDF file, I don't think there is a way currently to do this in MATLAB. The URLREAD function was the first thing I thought of to read content from a URL into a string, but it has this note in the documentation:
s = urlread('url') reads the content
at a URL into the string s. If the
server returns binary data, s will
be unreadable.
Indeed, if you try to read a PDF as in the following example, s contains some text intermingled with mostly garbage:
s = urlread('http://samplepdf.com/sample.pdf');
If you want to get the text from the PDF file, you have some options. First, you can use URLWRITE to save the contents of the URL to a file:
urlwrite('http://samplepdf.com/sample.pdf','temp.pdf');
Then you should be able to use one of two submissions on The MathWorks File Exchange to extract the text from the PDF:
Extract text from a PDF document by Dimitri Shvorob
PDF Reader by Tom Gaudette
If you simply want to view the PDF, you can just open it in Adobe Acrobat with the OPEN function:
open('temp.pdf');
wb=com.mathworks.mde.webbrowser.WebBrowser.createBrowser;
wb.executeScript('javascript:alert(''Some code from a link'')');
desk=com.mathworks.mde.desk.MLDesktop.getInstance;
desk.removeClient(wb);

Categories

Resources