When I test an app integrated with the HMS Health Kit on my Huawei Mate 30 Pro, why cannot I obtain the number of steps? - huawei-mobile-services

What should I do if the error code 50005 is returned when querying the step count using the corresponding method under DataController? (The scopes of Health Kit I applied for from the Huawei Developers website have been approved.)
2020-05-26 11:41:21.195 17338-17338/com.hauwei.hmsdemo I/DataManager:
read failure 50005:Unknown authorization error
2020-05-26 11:41:21.203 17338-17338/com.hauwei.hmsdemo I/DataManager:
The following lines are used for querying the step count:
public void readSteps(View view) throws ParseException {
DataCollector dataCollector = new DataCollector.Builder().setPackageName(context)
.setDataType(DataType.DT_CONTINUOUS_STEPS_DELTA)
.setDataStreamName("STEPS_DELTA")
.setDataGenerateType(DataCollector.DATA_TYPE_RAW)
.build();
SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd hh:mm:ss");
Date startDate = dateFormat.parse(BEGIN_TIME);
Date endDate = dateFormat.parse(END_TIME);
ReadOptions readOptions = new ReadOptions.Builder().read(dataCollector)
.setTimeRange(startDate.getTime(), endDate.getTime(), TimeUnit.MILLISECONDS)
.build();
dataController.read(readOptions).addOnSuccessListener(new OnSuccessListener<ReadReply>() {
#Override
public void onSuccess(ReadReply readReply) {
……
}
}).addOnFailureListener(new OnFailureListener() {
#Override
public void onFailure(Exception e) {
……
}
});
}

There is nothing wrong with the lines you used for querying the step count. The issue lies within authorization granting. It should be noted that the data that an app can access must be within the scopes granted to the app on the Huawei Developers website and within the range of data for which the user approval has been granted on the device side.
Regarding this issue, verify that the read/write permissions for the step count data have been granted when the app is displaying the data authorization screen.
You can refer to the following code, or refer to the sample code for Health Kit at
https://developer.huawei.com/consumer/en/doc/development/HMS-Examples/healthkit_Android_sample_code.
private void dataAuthorization() {
Log.i(TAG, "begin sign in");
// The data that can be used here and its read/write permissions can only be those you have applied for from the Huawei Developers website.
List < Scope > scopeList = new ArrayList < > ();
scopeList.add(new Scope(Scopes.HEALTHKIT_STEP_BOTH));
HuaweiIdAuthParamsHelper authParamsHelper =
new HuaweiIdAuthParamsHelper(HuaweiIdAuthParams.DEFAULT_AUTH_REQUEST_PARAM);
HuaweiIdAuthParams authParams =
authParamsHelper.setIdToken().setAccessToken().setScopeList(scopeList).createParams();
final HuaweiIdAuthService authService =
HuaweiIdAuthManager.getService(this.getApplicationContext(), authParams);
Task < AuthHuaweiId > authHuaweiIdTask = authService.silentSignIn();
authHuaweiIdTask.addOnSuccessListener(huaweiId - > {
......
}).addOnFailureListener(new OnFailureListener() {
#Override
public void onFailure(Exception exception) {
......
}
});
}

Related

UBER with SSO using uber rides-android-sdk

I'm trying to get data from ALL_TRIPS Scope. I'm running into a few issues.
1) once I add the Scope.All_Trips to the .setScopes I get redirected verse being able to login to obtain the Token, therefore I get the necessary data from the get CurrentRide() method.
configuration = new SessionConfiguration.Builder()
.setClientId(CLIENT_ID)
.setRedirectUri(REDIRECT_URI)
.setScopes(Arrays.asList(Scope.HISTORY, Scope.PROFILE, Scope.RIDE_WIDGETS, Scope.ALL_TRIPS))
.setEnvironment(SessionConfiguration.Environment.SANDBOX)
.build();
validateConfiguration(configuration);
Error: Webpage not available The webpage at
Market://details?hl-en&id=com.ubercab&referrer=mat_cli%3
And it goes on and one.
Once i remove the All_TRIPS SCOPE I get the ability to Sign in.
Any help would be great so that I can move forward with getting the details like driver, vehicle, RideID.
private void LoadAllTrips(){
Session session = loginManager.getSession();
RidesService AllTrips = UberRidesApi.with(session).build().createService();
AllTrips.getCurrentRide().enqueue(new Callback<Ride>() {
#Override
public void onResponse(Call<Ride> call, Response<Ride> response) {
if (response.isSuccessful())
{
Toast.makeText(LoginSampleActivity.this, response.body().getRideId(), Toast.LENGTH_LONG).show();
}
else
{
ApiError error = ErrorParser.parseError(response);
Toast.makeText(LoginSampleActivity.this, error.getClientErrors().get(0).getTitle(), Toast.LENGTH_LONG).show();
}
}
#Override
public void onFailure(Call<Ride> call, Throwable t) {
}
});
}

Parse query always returns an empty list

I have the following problem:
I have two Android apps: In one app I add data to Mongo DB via Parse and in the other app I want to retrieve the information added from the first app.
The problem is that in the second app everytime I try to query the DB, I get an empty list. I`ve checked with the API KEY, with the keys from the Mongo DB, and everything seems ok in my app.
Here is the code for the second app to retrieve information in a RecyclerView
public class ParseDb extends Application {
#Override
public void onCreate() {
super.onCreate();
// Enable Local Datastore.
Parse.enableLocalDatastore(this);
// Add your initialization code here
Parse.initialize(new Parse.Configuration.Builder(getApplicationContext())
.applicationId(API_KEY)
.server("http://injuriesandsuspensions.herokuapp.com/parse/")
.build()
);
ParseUser.enableAutomaticUser();
ParseACL defaultACL = new ParseACL();
// Optionally enable public read access.
defaultACL.setPublicReadAccess(true);
ParseACL.setDefaultACL(defaultACL, true);
}
public class MainActivity extends Activity {
private List<AboutTeams> aboutTeamsList = new ArrayList<AboutTeams>();
private RecyclerView recyclerView;
private GamesAdapter gamesAdapter;
public void retrieveGamesFromDatabase(){
ParseQuery<ParseObject> query = ParseQuery.getQuery("InjuriesAndSuspensions");
query.whereEqualTo("score", "none");
query.findInBackground(new FindCallback<ParseObject>() {
public void done(List<ParseObject> gamesList, ParseException e) {
if (e == null) {
Log.d("score", "Retrieved " + gamesList.size() + " scores");
for(int i = 0; i < gamesList.size(); i++){
AboutTeams aboutTeams = new AboutTeams();
aboutTeams.setId(String.valueOf(gamesList.get(i).getObjectId()));
aboutTeams.setScore(String.valueOf(gamesList.get(i).get("score")));
aboutTeams.setHomeTeam(String.valueOf(gamesList.get(i).get("homeTeam")));
aboutTeams.setHomeTeamMissing(String.valueOf(gamesList.get(i).get("homeTeamMissingPlayers")));
aboutTeams.setAwayTeam(String.valueOf(gamesList.get(i).get("awayTeam")));
aboutTeams.setAwayTeamMissing(String.valueOf(gamesList.get(i).get("awayTeamMissingPlayers")));
aboutTeams.setDate(String.valueOf(gamesList.get(i).get("gameDate")));
Log.d("About Teams " , aboutTeams.toString());
aboutTeamsList.add(aboutTeams);
gamesAdapter.notifyDataSetChanged();
}
} else {
Log.d("score", "Error: " + e.getMessage());
}
}
});
}
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main_listview);
recyclerView = (RecyclerView) findViewById(R.id.recycler_view);
gamesAdapter = new GamesAdapter(aboutTeamsList);
RecyclerView.LayoutManager mLayoutManager = new LinearLayoutManager(getApplicationContext());
recyclerView.setLayoutManager(mLayoutManager);
recyclerView.setItemAnimator(new DefaultItemAnimator());
recyclerView.setAdapter(gamesAdapter);
retrieveGamesFromDatabase();
}
Please help as I`ve been struggling with this thing for almost 3 days.
When I was adding info to the Collection DB,the ParseObject I was using didn`t have this line added where I was initializing Parse in my application:
defaultACL.setPublicReadAccess(true);
Complete code on how to initialize Parse:
public class AddToDB extends Application {
#Override
public void onCreate() {
super.onCreate();
// Enable Local Datastore.
Parse.enableLocalDatastore(this);
// Add your initialization code here
Parse.initialize(new Parse.Configuration.Builder(getApplicationContext())
.applicationId(API_KEY)
.server(SERVER_URL)
.build()
);
ParseUser.enableAutomaticUser();
ParseACL defaultACL = new ParseACL();
// Optionally enable public read access.
**defaultACL.setPublicReadAccess(true);**
ParseACL.setDefaultACL(defaultACL, true);
}
}

Uploading image to Google Drive using GWT-Google Picker

I am trying to upload an image to Google Drive using Google Picker user interface. So far i have been unsuccessful.
This is the code that i am using :
private void onCreatePicker(ViewId viewId) {
final Picker picker = PickerBuilder.create()
.setTitle("Subir imagen a Google Drive")
.addView(viewId)
.addView(DocsUploadView())
.setLocale("es")
.setOAuthToken(token_oauth2)
.setDeveloperKey(DEVELOPER_KEY)
.setCallback(buildPickerCallback(viewId))
.build();
picker.setVisible(true);
}
private JavaScriptObject DocsUploadView() {
return com.ip.gae.gartla.shared.DocsUploadView.create();
}
I request your help on what could i be missing.
Thank you for your time,
Regards,
UPDATE: It seems that my application scope was wrong. In order to generate the correct oAuth2Token, you must declare the scope which you want to generate the token for:
The following its the method I am using to generate the token:
private void tokenOauth2() {
AuthRequest req = new AuthRequest(AUTH_URL, CLIENT_ID)
.withScopes(GOOGLE_DRIVE_SCOPE); // Can specify multiple scopes here
Auth.get().login(req, new Callback<String, Throwable>() {
#Override
public void onSuccess(String token) {
token_oauth2 = token;
}
#Override
public void onFailure(Throwable caught) {
// The authentication process failed for some reason, see caught.getMessage()
}
});
}
And here it is the GOOGLE_DRIVE_SCOPE variable that i am using:
String GOOGLE_DRIVE_SCOPE = "https://www.googleapis.com/auth/drive";
So, for now this is working for me. I have attached the solution so if someone finds it out interesting enough. :-)

What causes a lock on an entity table in QuickBooks Online API?

I'm trying to optimize my application to perform at maximum speed. I intended on having two threads each executing a batch request of sales receipts additions. I also intended on having two parallel threads each with a batch request of customer additions. I was wondering whether this is possible or would the API lock the sales receipt/customer table in QuickBooks thus only allowing one thread to perform.
From my research I know that there a three types of entities (Name list, transaction and supporting entities). So what are the causes of locks on these entities, ie what scenario's will cause a lock? Is there any documentation on this matter I couldn't seem to find any?
Thanks
Lock is applicable for Name entities(Vendor, Customer and Employee ). While creating a new name entity, service ensures that an unique name is getting inserted in cloud. So, it puts a lock across all names of these 3 entities.
You can try this scenario using a decent payload.
public static void main(String args[]) {
PropertyConfigurator
.configure("log4j.properties");
Config.setProperty(Config.SERIALIZATION_REQUEST_FORMAT, "xml");
Config.setProperty(Config.SERIALIZATION_RESPONSE_FORMAT, "xml");
final Context platformContext = getPlatformContext("QBO");
final QBOV3ProdTest qbov3ProdTest = new QBOV3ProdTest(platformContext);
Thread customerThread = new Thread(new Runnable() {
#Override
public void run() {
for (int i = 0; i < 15; i++) {
qbov3ProdTest.addCustomer();
}
}
});
customerThread.start();
Thread vendorThread = new Thread(new Runnable() {
#Override
public void run() {
for (int i = 0; i < 15; i++) {
qbov3ProdTest.addVendor();
}
}
});
vendorThread.start();
}
private void addCustomer() {
Customer customer = new Customer();
customer.setDisplayName("TestCustomer-" + staticCount++);
try {
this.service.add(customer);
} catch (FMSException e) {
e.printStackTrace();
}
}
private void addVendor() {
Vendor vendor = new Vendor();
vendor.setDisplayName("TestVendor-" + staticCount++);
try {
this.service.add(vendor);
} catch (FMSException e) {
e.printStackTrace();
}
}
Service doesn't return a proper response. Wherever it fails, service returns 401. Please let me know if you can reproduce this behaviour while trying this use-case in your test QBO account.
Thanks
This is not exactly a DB locking rule but because of the way we are saving data to our cache for Names lists.
We do not allow users to update these entities in a multi-threaded manner:
Account,
Department,
Item,
Class,
Customer,
Employee,
Vendor,
PaymentMethod,
Terms.
The above has been confirmed by our engineering team.

Multiple impersonation-threads in Exchange Web Service (EWS)

I have a problem when running multiple impersonations of users in EWS, when I want to recieve notifications on each of the impersonated persons calendars (possible 100 persons).
Currently I have an outlook account who have rights to impersonate all other users, and all the ExchangeService-objects get this accounts credentials
Short version is, that when I try to bind to an appointment via the unique ID it works as long as I only have one thread running. When I start a new thread containing a new Exchangeservice with its own subscription I dont recieve any response on the Appointment.Bind()-request.
When I run two instances of my program with only 1 thread in each it works fine, but as soon as I start a new thread with a new ExchangeService the Appointment.Bind() doesnt give any response.
The weird part about this is, that it worked fine two weeks ago, but suddenly it stopped working and I didnt change my code.
I have created a quick demo of my problem:
class Program
{
static void Main(string[] args)
{
var x = new OutlookListener("user1#server.com");
var y = new OutlookListener("user2#server.com");
new Thread(x.Start).Start();
new Thread(y.Start).Start();
while (true)
{
}
}
}
class OutlookListener
{
private ExchangeService _ExchangeService;
private AutoResetEvent _Signal;
public OutlookListener(string emailToImp)
{
_ExchangeService = new ExchangeService(ExchangeVersion.Exchange2010_SP1)
{
Credentials = new NetworkCredential("superuser#server.com", "password"),
Url = new Uri("exchangeUrl"),
ImpersonatedUserId = new ImpersonatedUserId(ConnectingIdType.SmtpAddress, emailToImp)
};
}
public void Start()
{
var subscription = _ExchangeService.SubscribeToStreamingNotifications(new FolderId[] { WellKnownFolderName.Calendar },
EventType.Created);
var connection = CreateStreamingSubscription(_ExchangeService, subscription);
Console.Out.WriteLine("Subscription created.");
_Signal = new AutoResetEvent(false);
_Signal.WaitOne();
subscription.Unsubscribe();
connection.Close();
}
private StreamingSubscriptionConnection CreateStreamingSubscription(ExchangeService service, StreamingSubscription subscription)
{
var connection = new StreamingSubscriptionConnection(service, 30);
connection.AddSubscription(subscription);
connection.OnNotificationEvent += OnNotificationEvent;
connection.OnSubscriptionError += OnSubscriptionError;
connection.OnDisconnect += OnDisconnect;
connection.Open();
return connection;
}
private void OnNotificationEvent(object sender, NotificationEventArgs args)
{
// Extract the item ids for all NewMail Events in the list.
var newMails = from e in args.Events.OfType<ItemEvent>()
where e.EventType == EventType.Created
select e.ItemId;
foreach (var newMail in newMails)
{
var appointment= Appointment.Bind(_ExchangeService, newMail); //This is where I dont get a response!
Console.WriteLine(appointment.Subject);
}
}
private void OnSubscriptionError(object sender, SubscriptionErrorEventArgs args)
{
}
private void OnDisconnect(object sender, SubscriptionErrorEventArgs args)
{
}
}
Any suggestions?
I have had the same issue and found that my EWS solution was limited by two factors.
The System.Net.ServicePointManager.DefaultConnectionLimit is by default set to 2, which I've changed to 20 which i beleive to match the throttling policy of Exchange Online.
Second the ConnectionGroupName property on the ExchangeService object can be used to pool connections into different relevant groups which have a limit of concurrent connections cohernet with the DefaultConnectionLimit property.
A way to override the settings is to set the ConnectionGroupName property to a uniquevalue for each ExchangeService object you create.
ExchangeService exchangeService = new ExchangeService()
{
ConnectionGroupName = Guid.NewGuid().ToString()
};
Why do you need multiple threads ?
In my case , I have created a dictionary of Services based on the smtpaddress for each email I want to impersonate, and I subscribe to them all. All can happen in one thread, and all notification from any user will be handled in the OnNotificationEvent .
[THIS CODE IS JUST TO SHOW THE LOGIC AND IS NOT COMPLETE FOR FULL COMPILATION AND RUN]
var service = new ExchangeService(exchangeVersion);
var serviceCred = ((System.Net.NetworkCredential)(((WebCredentials)(Services.First().Value.Credentials)).Credentials));
service.Credentials = new WebCredentials(serviceCred.UserName, serviceCred.Password);
service.AutodiscoverUrl(userSmtp, RedirectionUrlValidationCallback);
service.ImpersonatedUserId = new ImpersonatedUserId(ConnectingIdType.SmtpAddress, userSmtp);
Services.Add(userSmtp, service);
Note that Services.First().Value is the service that can impersonate all the other users, and here it is cloned as the number of the user.
After that Subscriptions for the all services (note that now each service is impersonating different user)
foreach (var service in Services.Values)
{
SubscribeToService(service);
}
and the definition for SubscribeToService is as follow
private void SubscribeToService(ExchangeService service)
{
if (service.ImpersonatedUserId == null)
return;
if (service.Url == null)
return;
var serviceName = service.ImpersonatedUserId.Id;
var streamingSubscription =
service.SubscribeToStreamingNotifications(new FolderId[] { WellKnownFolderName.DeletedItems, WellKnownFolderName.Calendar },
EventType.FreeBusyChanged, EventType.Moved, EventType.Created, EventType.Modified);
if (!Connections.ContainsKey(service.Url))
{
Connections.Add(service.Url, new StreamingSubscriptionConnection(service, 30));
}
var connection = Connections[service.Url];
CloseConnection(connection);
if (!_subscriptions.ContainsKey(serviceName))
{
_subscriptions.Add(serviceName, streamingSubscription);
connection.AddSubscription(streamingSubscription);
}
}
}
All of this can happen in one single thread, and I hope my answer will help you
Cheers