I created an app with expo where some report in xlsx is generated in a server and then downloaded to the Download folder in Android. I want to "open" the file after it was downloaded by using another app with the open with native modal. I tried the following:
static openFile = async (asset, contentType) => {
return IntentLauncher.startActivityAsync('android.intent.action.VIEW', {
data: asset.uri,
type: contentType,
});
};
(contentType is currently receiving '*/*') but it fails everytime with the following error:
Encountered an exception while calling native method: Exception occurred while executing exported method startActivity on module ExpoIntentLauncher: file:///storage/emulated/0/Download/report-10010654-20210304061930069176.xlsx exposed beyond app through Intent.getData()
One solution is using the Sharing library, but I'm not overjoyed with it. Is there any way to make it work without ejecting from the managed flow?
I had a similar problem a month ago, I think it happens when startActivityAsync is called multiple times, my solution was to wrap my code in a try statement:
const data = await getContentUriAsync(uri)
try {
await startActivityAsync('android.intent.action.VIEW', { data, flags: 1 })
} catch (error) {}
Related
I've got a very simple cloud function that returns a string in a JSON.
const functions = require("firebase-functions");
// Create and Deploy Your First Cloud Functions
// https://firebase.google.com/docs/functions/write-firebase-functions
exports.helloWorld = functions.https.onRequest((request, response) => {
functions.logger.info("Hello logs!", {structuredData: true});
response.send({data: "Hello from Firebase!"});
});
And I am calling it like this(app is running in android emulator):
async function callFirebaseCloudFunction() {
try
{
functions().useEmulator('localhost', 5001);
const helloWorldFunction = functions().httpsCallable('abcd');
const response = await helloWorldFunction();
console.log(response?.data);
alert(response?.data);
}
catch (error)
{
console.log("====",error);
alert(`${JSON.stringify(error)}` );
}
}
The issue is that I am getting DEADLINE_EXCEEDED error.
Note that I am also running firebase's emulator for cloud function, therefore this line:
functions().useEmulator('localhost', 5001);
Otherwise, commenting the above line and calling the deployed function works fine.
After spending more than an hour, and writing this question. I finally figured out the problem(kind of), so I thought I should just answer it.
I was using the android emulator of Genymotion, and the request kept failing "DEADLINE_EXCEEDED" error. When I used avd(android virtual device from Android Studio), it worked totally fine.
I'm currently building a simple app in React Native 0.62.2 for Android. I've been having some trouble with axios 0.19.2 (or even the fetch API) when trying to upload images to my API (which is written in node.js/express). The POST request is formulated as follows:
// UserService.js
export const postNewUser = async (newUser) => {
try {
const photo = {
uri: newUser.avatar.uri,
type: 'image/jpg',
name: newUser.avatar.fileName,
};
const formData = new FormData();
Object.keys(newUser).forEach(key => formData.append(key, newUser[key]));
formData.append('avatar', photo);
const response = await api.post('/users', formData);
return response.data;
} catch (err) {
console.log('TRACE error posting user: ', err);
return;
}
}
Here, the property newUser.avatar.uri is set by means of an image picker library, namely #react-native-image-picker 1.6.1. It gives me a NetworkError whenever I append the photo variable into the FormData. Setting the URI manually with some random image from the web results in the same error. Debbuging it from the Browser, it prints out some sort of stack trace like this one:
TRACE error posting user: Error: Network Error
at createError (C:\Users\Dell\Documents\Projetos\SmartestVet\node_modules\axios\lib\core\createError.js:16)
at EventTarget.handleError (C:\Users\Dell\Documents\Projetos\SmartestVet\node_modules\axios\lib\adapters\xhr.js:83)
at EventTarget.dispatchEvent (C:\Users\Dell\Documents\Projetos\SmartestVet\node_modules\event-target-shim\dist\event-target-shim.js:818)
at EventTarget.setReadyState (C:\Users\Dell\Documents\Projetos\SmartestVet\node_modules\react-native\Libraries\Network\XMLHttpRequest.js:575)
at EventTarget.__didCompleteResponse (C:\Users\Dell\Documents\Projetos\SmartestVet\node_modules\react-native\Libraries\Network\XMLHttpRequest.js:389)
at C:\Users\Dell\Documents\Projetos\SmartestVet\node_modules\react-native\Libraries\Network\XMLHttpRequest.js:502
at RCTDeviceEventEmitter.emit (C:\Users\Dell\Documents\Projetos\SmartestVet\node_modules\react-native\Libraries\vendor\emitter\EventEmitter.js:189)
at MessageQueue.__callFunction (C:\Users\Dell\Documents\Projetos\SmartestVet\node_modules\react-native\Libraries\BatchedBridge\MessageQueue.js:425)
at C:\Users\Dell\Documents\Projetos\SmartestVet\node_modules\react-native\Libraries\BatchedBridge\MessageQueue.js:112
at MessageQueue.__guard (C:\Users\Dell\Documents\Projetos\SmartestVet\node_modules\react-native\Libraries\BatchedBridge\MessageQueue.js:373)
If I, for example, comment out the line formData.append('avatar', photo); it works perfectly, i.e., my API receives the request accordingly. So I think this might not be a CORS-related issue. Also, other requests, such as GETs and even other POSTs are working just fine.
I know there's a bunch of other related posts here in SO and also in GitHub, some of them related to the exact same issue. But none of the solutions I found worked out for me.
In case someone wants to check out how the routes in my API are implemented just hit me up and I will provide the code here.
Thanks in advance for any help you might give me!
I'm having the same issue, using the formData but without the file upload it works just fine. I did a lot of research and what I've found is an old issue that still's active in the react native repo. The solution that's suggested is using a library called rn-fetch-blob but I couln't implement it on my project. If you can make it work share your work around please.
My question is that, if it is possible to get a variable from a .properties or .txt file. I need that in order to save the endPoint, the server IP address. That way, every time that the IP address is changed, all you need to do is change the IP on the file, instead of compile the code again and build the apk, and install it again on the device. Any tips will be welcome.
UPDATE
I've been trying to use this plugin :File , but with no sucess. I want to use readAsText(path,file) but all i get is undefined
import { File } from '#ionic-native/file/ngx';
constructor(
....
private file : File,
....
) { }
async test(){
this.promise = this.file.readAsText('file:///data/','ipAddress.txt');
await this.promise.then(value => {
console.log(value)
}).catch(error=> console.log("nao existe"))
}
And i'm getting the following error:
ERROR Error: Uncaught (in promise): FileError: {"code":1,"message":"NOT_FOUND_ERR"}
UPDATE
Problem Solved. I was trying to acess to the internal storage, and the document was on the external storage. Make sure you use URI, path on android are different from computer. You need URI.
file:///storage/emulated/0/Android/data/
I called the method right on, when device's ready on app.component.ts
ngOnInit() {
.....
this.initializeApp();
}
initializeApp() {
this.platform.ready().then(() => {
this.api.getURL();
.....
});
}
Hope i can help the next with the same problem I had.
Works in IOS and works in Android when the debugger is running, but doesn't work via Android Simulator. I get this message via react-native log-android and basically I am just having nothing returned to the screen:
12-02 10:39:58.511 22502 24204 W ReactNativeJS: TypeError: undefined is not a function (near '...}).flat()
Android Picture
IOS Picture
Here is the fetch function I am using:
import axios from 'axios';
export const getData = async url => {
try {
const response = await axios.get(url);
const data = response.data;
return data;
} catch (error) {
console.log(error);
}
};
export default getData;
Inside of my componentDidMount, where I call the endpoint using the GetData function above:
componentDidMount() {
const teamsAPI = 'https://statsapi.web.nhl.com/api/v1/teams';
getData(teamsAPI).then(teams => {
const teamData = teams.teams
.map(({ id, name }) => ({
teamId: id,
teamName: name
}))
.flat()
this.setState({
teams: teamData
});
});
}
Everything has since been moved to REDUX, but I looked back at one of my branches today with the more basic code shared above and had the issue back then with this code as well. Unfortunately didn't realize all the differences with code compilations till now. Understand that the issue is probably because of 2 compilers, but have no idea how to approach the issue/ why there would be a type error in one and not the other.
It works with debugger I think due to what was mentioned here:
React Native behavior different in simulator / on device / with or without Chrome debugging
Edit: wanted to mention I've already done a cache reset and deleted the build folder and rebuilt
I tried out your code and the promise rejecting is happing for me in both Android and iOS. It is being caused by the .flat() removing it stops the promise rejection from occurring.
Looking at the data that you are mapping there there doesn't seem to be a need to flatten the data as it comes back as a array of objects with no other arrays inside it.
Could removing the .flat() be a possible solution for you?
You can see here for more information about .flat() and how it is still experimental array.prototype.flat is undefined in nodejs
I would also consider returning something from your getData function when it makes an error or perhaps use a promise with it that way you can handle an error.
I have a Cordova app that uses the ionic framework. I have many json data files that I put in the www/json folder in my app's file tree. I am using angularJS http calls to access them.
When I test my app in chrome (using "ionic serve" in the terminal) it works fine but when I test it on an android device(nexus 5 with Android 6.0 Marshmallow) it no longer works.
Sample code
function getBookNames() {
return $http.get("..\\bookfolder\\Books.json")
.then(function (data) {//if success than do
return data.data;
}, function (reason) {// if fail than do
// maybe tell the user what happened...
});
}
I have tried adding
var path = "";
if (ionic.Platform.isAndroid()) {
path = "\\android_asset\\www\\";
}
function getBookNames() {
return $http.get(path + "..\\bookfolder\\Books.json")
.then(function (data) {//if success than do
return data.data;
}, function (reason) {// if fail than do
// maybe tell the user what happened...
});
}
when I am debugging the app on my phone I get the following error.
GET file:///android_asset/bookfolder/Books.json net::ERR_FILE_NOT_FOUND
If anyone knows what I am doing wrong or of a better way to access local .json files please let me know. Thanks!
Use slash / character, not backslash \. Also, put bookfolder inside /android_asset/www
$http
.get('/android_asset/www/bookfolder/books.json')
.then(function(response){ return response.data });