How to retrieve a single contact with gdata? Getting a 'not supported' error - google-contacts-api

I'm copying the code here https://developers.google.com/google-apps/contacts/v3/#retrieving_a_single_contact.
And here's my code:
Dim cr = ContactAuthentication()
Dim groups = GetGroups(cr)
Dim entry As Contact
entry = cr.Retrieve(Of Contact)(New Uri("https://www.google.com/m8/feeds/contacts/default/full/38B2D4F80D96B2C2"))
On the last line, it falls with the following error:
Google.GData.Client.GDataRequestException: 'Execution of request
failed:
https://www.google.com/m8/feeds/contacts/default/full/38B2D4F80D96B2C2?max-results=100'
"The 'max-results' parameter is not supported on this
resource"
Which is odd, since I never put in a max result parameter. Also, if it makes any difference, the Google docs show an example that takes a string url as the param for Retrieve. I could not find such an overload, the closest is what I put here, using a Uri
Anyone have any ideas how I can retrieve a single contact by id for updating?
Thanks!

You may refer with this documentation: Retrieving a single contact. To retrieve a single contact, send an authorized GET request to the contact's selfLink URL:
https://www.google.com/m8/feeds/contacts/{userEmail}/full/{contactId}
With the appropriate values in place of userEmail and contactID. Be noted that the special userEmail value default can be used to refer to the authenticated user.
And as referred with this post, maybe you had setting.Pagesize = 100, which caused your uri to be https://www.google.com/m8/feeds/contacts/{userEmail}/full/{contactId}?max-results=100.
Hope this helps!

Related

Power Query M - Expression Error - list to text

I'm doing a API request using Web.Contents. I submit a dynamic access token, which I get from a function.
let
Source =
Json.Document(
Web.Contents(
{"https://api-url.com/endpoint/id"},
[Headers=[Authorization="Bearer "& GetToken()]]))
in Source
This works in all of my other instances, but for some reason I get an error with a specific endpoint, to which I submit a id. The error is:
Expression.Error: We cannot convert a value of type List to type Text.
Details:
Value=[List]
Type=[Type]
I have checked the documentation for the API, and the response is composed of the following
id - Id of the device
lastServicedDate - The last time the service was done.
trip -
total -
stateLastUpdated - the timestamp of the state.
Previous assistance have informed me that I need to expand the list, but I cannot seem to make this work.
Any assistance is highly appreciated. Thank you.
You are supplying a list to Web.Contents instead of text. {} denotes a list. Remove your braces:
Web.Contents(
"https://api-url.com/endpoint/id",
[Headers=[Authorization="Bearer "& GetToken()]])

How to include SR related work log long description when using maximo oslc rest api?

I am doing an HTTP GET request to /maximo/oslc/os/mxsr and using the oslc.select query string parameter to choose:
*,doclinks{*},worklog{*},rel.commlog{*},rel.woactivity{*,rel.woactivity{*}}
This lets me get related data, including related worklogs, but the worklog does not include the 'description_longdescription' field.
The only way I seem to be able to get that field is if I do a separate HTTP GET to query a worklog id directly through /maxrest/rest/mbo/worklog . Then it provides the description_longdescription field.
I understand this field is stored separately through the linked longdescription table, but I was hoping to get the data through the "next gen" oslc api with one http get request.
I've tried putting in 'worklog{*,description_longdescription}', as I read somewhere that longdescription is a "non-persistent" field and must be explicitly named for inclusion, but it had no effect.
I figured out that for the /maximo/oslc/os/mxsr object in the API, I needed to reference the related MODIFYWORKLOG object through the rel.modifyworklog syntax in the oslc.select query string:
oslc.select=*,doclinks{*},rel.modifyworklog{*,description_longdescription},rel.commlog{*},rel.woactivity{*,rel.woactivity{*}}
I also had to explicitly name the non-persistent field description_longdescription for it to be included.
Ref. for the "rel." syntax: https://developer.ibm.com/static/site-id/155/maximodev/restguide/Maximo_Nextgen_REST_API.html#_querying_maximo_asset_management_by_using_the_rest_api

ContactsApp.getContact() for contact with multiple emails returns a different contact for each email address

My company allows employees to have multiple email addresses in their account.
I am attempting to write an input form where someone can enter any of the emails for a contact and we'll resolve it to the same person.
I've tried doing this via ContactsApp.getContact(email).getPrimaryEmail() to resolve all different inputs to the same primary email, but it doesn't work as expected. Each email I search for returns a different Contact object with only a single email (the one I used to search).
Even if I use ContactsApp.getContact(email).getEmails() to list all emails to the employee, I can see it only returns one at a time.
When going to contacts.google.com, I see the information I expected. Searching for any of the emails will return the same contact, with the same primary email and all other emails listed.
Is there something I'm doing wrong? Or is this how ContactsApp works. If so, is there a workaround?
Thanks!
getPrimaryEmail() will only return an email address if the contact in question has had a default email set and this can only be done via the Google Contacts App, not on the web (go figure).
To solve your problem I would suggest loading all the contacts into an array variable first and then searching this for matching email addresses. I would do the data retrieval on page/view load (so it can be reused without multiple server calls) but have included it all together here for conciseness.
What I found strange about the ContactsApp (and presumable People API too) is that the contacts returned are just empty objects (when logged) with just a bunch of methods on them. However, once you have an array of objects you can write your own properties to those objects for easier access of data.
Therefore I would first of all retrieve all the users contacts, then add a property of .emails to each contact object in the array and then use .some, perhaps, to check if a match appears in .emails (which will also be an array).
Something like:
let strSearch = 'someone#somewhere.net' // EMAIL address to search based on user input
let arrContacts = ContactsApp.getContacts();
let contacts = arrContacts.map(contact => {
let emails = contact.getEmails();
contact.emails = emails.map(email => email.getAddress());
return contact;
});
let foundContact = contacts.filter(contact => contact.emails.some(email => email === strSearch));
Remember .getEmails() returns another array of objects that have the method .getAddress() on them in order to retrieve the actual address, that's why I'm getting an array of email objects with let emails = contact.getEmails(); then using emails.map here to put the actual email addresses into an array stored in the contact.emails property (that doesn't exist so we're actually creating it here).
After that we're filtering the contacts array down to a contact where the searched email address is matched to one of the email addresses in the contact.emails array. I haven't tested it so the last line might need playing around with slightly but I've used something very similar so would expect it to work.
You can then use foundContact[0] to reference the contact found and use the further methods of .getFullname() .getId() etc. to retrieve their data as required. If you need the contacts phone numbers or geographical address that's a whole other process of returning an array of objects using .getPhones() or getAddresses(), but I think that's beyond the scope of this question.

StudentSubmissions.Patch UpdateMask Error

Trying to use the StudentSubmissions.Patch part of the Classroom API in Google Apps Script and keeping running across this error
updateMask: updateMask may only contain "draftGrade" or
"assignedGrade"
Here is my code for that particular section:
var studentSubmission = {'draft_grade':'88'}
var patchC = Classroom.Courses.CourseWork.StudentSubmissions.patch(studentSubmission, courseId, cwId, submissionId);
There is clearly something wrong with the way I am passing the StudentSubmission Resource parameter, but I can't figure out why...
This is clearly the documentation I am referring to - https://developers.google.com/classroom/reference/rest/v1/courses.courseWork.studentSubmissions/patch
UPDATE
I was able to change the code a bit to reflect what you both were saying. Obviously, I didn't use exactly what you both said because KENdi's example is in Python and Ein2012, it would error out on the var patchC = Classroom... line.
I changed some things that now look like this:
var studentSubmission = {'draftGrade':'88'}
var extra = {'updateMask':'draftGrade'};
var patchC = Classroom.Courses.CourseWork.StudentSubmissions.patch(studentSubmission, courseId, cwId, submissionId, extra);
But now I get a different error "#ProjectPermissionDenied The Developer Console project is not permitted to make this request". So, now I'm unsure if that formatting is correct and there is some Developer Console situation I haven't resolved (although feel as though I'm correct), or that new formatting is wrong and I'm just getting the wild permission error.
I saw this Similar Error but what if the course work was one created normally through classroom and not via a script? Ahh.
specify update mask fields and later execute and also specify names as instructed in the documentation ("draftGrade","assignedGrade")
var studentSubmission = {'draftGrade':'88'}
var patchC = Classroom.Courses.CourseWork.StudentSubmissions.patch(studentSubmission, courseId, cwId, submissionId);
patchC.UpdateMask = "draftGrade";
var response = submisionObj.Execute();
From your error, it is stated that the updateMask must only contain "draftGrade" or "assignedGrade". So from your code, you need only that two value for the updateMask.
The updateMask identifies which fields on the student submission to update. This field is required to do an update. The update fails if invalid fields are specified
From this documentation, The StudentSubmission resource has two fields to store grades: assignedGrade, which is the grade reported to students, and draftGrade, which is a tentative grade visible only to teachers. These fields are updated using courses.courseWork.studentSubmissions.patch with a field mask containing the appropriate fields.
Here is the example code on how to do that.
studentSubmission = {
'assignedGrade': 99,
'draftGrade': 80
}
service.courses().courseWork().studentSubmission().patch(
courseId=<course ID or alias>,
courseWorkId=<courseWork ID>,
id=<studentSubmission ID>,
updateMask='assignedGrade,draftGrade',
body=studentSubmission).execute()

Box API: Get_managed_users returning all users

Using the Box 1.0 REST API, I am trying to work with the functions in SOAP UI.
The API doc for get_managed_users with user_id=12345 (internal id retrieved with get_user_id call correctly) is returning all the users. The docs say that would be the case if you do not specify a user_id value. But my full command is: (Token and API key changed to protect the clueless)
https://www.box.com/api/1.0/rest?user_id=27360&auth_token=blahbalhblah1234&action=get_managed_users&api_key=someKeyYouShouldNotSee
Now I could work with the complete result list, but that won't scale as we get thousands of users into the system.
I can make a call with edit_managed_user, using the same user_id value and the change is reflected in the UI, and in the next get_managed_users call. Thus I do have the correct user_id value, I would so assume.
I tried testuser#gmail.com as the user_id value as well, and get the entire list back. This leads me to believe that somehow I am sending user_id wrong, but I just do not see it.
Any hints? Why, with what seems like a valid user_id value is it acting like it is absent or incorrect?
Most likely you have either called this method with an invalid user_id, or one that is not in your set of managed users. Can you double check that the user comes back in your list of already managed users?