I am passing event.params as json string. But the value not reflecting in google big query.
Here screen and name is coming in big query.
const params = {
screen: screen,
name:name,
event_params: JSON.stringify({
source: source,
user_id: user_id,
}),
}
this._logEvent(EventValues.ScreenView, params)
I can see in the browser network data is passing.
Before i tried without stringify also, its not working
Related
I'm building a React Native app with Expo, and I want to include the following workflow: The user takes a picture (either with the camera or picking one from the phone's gallery), which is stored locally on the phone, until the user uploads it some later time to a backend service.
I'm pretty stuck and would appreciate any pointers.
Here is what I have:
I use expo-image-picker to pick a photo from the phone's gallery:
const photo = await launchImageLibraryAsync({
mediaTypes: ImagePicker.MediaTypeOptions.All,
allowsEditing: true,
base64: true,
quality: 1,
});
Then I store the photo locally as a Base64 string using expo-file-system:
const location = `${FileSystem.documentDirectory}${filename}`;
await FileSystem.writeAsStringAsync(location, photo.base64, {
encoding: FileSystem.EncodingType.Base64
});
I keep information about the storage location, file name, and mime type in an image object. Later, I try to upload that image to my own Node.js backend service with axios, sending the following multi-part form data:
const formdata = new FormData();
formdata.append('file', {
path: image.location,
name: image.filename,
type: image.mimetype
} as any);
The backend service that receives the photo uses multer:
const multer = require('multer');
const upload = multer({ storage: multer.memoryStorage() });
router.post('/photo', upload.single('file'), async (request, response) => {
console.log(request.file);
...
});
What arrives at my service is the following:
{
fieldname: 'file',
originalname: '1653135701413.jpg',
encoding: '7bit',
mimetype: 'image/jpg',
buffer: <Buffer >,
size: 0
}
So no data is transferred. (It seems to be properly stored on the phone, because if I use the Expo filesystem's readStringAsAsync, I do get a pretty long Base64 string.)
What am I missing? Do I need to send the image as a blob? (If I try to do so, then request.file is undefined, so I guess I'm doing something wrong there as well.)
And in general, is there a better way to achieve this workflow in a managed React Native app? (For example, is it ok to store the image as a Base64 string, or would it be better to do this differently?)
Edit:
In the form data, I changed path to uri, and I switched from axios to fetch. Now the backend finally receives the image data. 🥳
i'm using Nuxt
I'm having troubles with passing data from one page to another
I would like programmatically to navigate to other page, and pass some data to other page (in this case its javascript object)
So here is my code so far:
I have a component in which I navigate from:
this.$router.push({ path: 'page/add', props: { basket: 'pie' } });
And here is a component where I would like to get data, its a Nuxt page:
export default {
components: { MyComponent },
props: [
'basket' // this is also empty
],
async asyncData(data) {
console.log(data); // data does not contain basket prop
},
meta: {
breadcrumb: {
path: '/page/add',
},
},
};
</script>
But when I try to acces props, or data or data.router it does not contain basket prop ??
Also, I would not like to use query, or params because they change URL
[1]: https://nuxtjs.org/
You can use localstorage and save you'r data in it:
localStorage.setItem("nameOfItem", Value);
and delete it if you want after you'r done with it:
localStorage.removeItem("nameOfItem");
If you don't want to use query or params, I would check out the vuex store. Its a really cool way of storing global variables and use it in multiple pages.
Vuex store
Navigate to a different location
To navigate to a different URL, use router.push. This method pushes a new entry into the history stack, so when the user clicks the browser back button they will be taken to the previous URL.
The argument can be a string path, or a location descriptor object. Examples:
// literal string path
this.$router.push('/users/eduardo')
// object with path
this.$router.push({ path: '/users/eduardo' })
// named route with params to let the router build the url
this.$router.push({ name: 'user', params: { username: 'eduardo' } })
// with query, resulting in /register?plan=private
this.$router.push({ path: '/register', query: { plan: 'private' } })
// with hash, resulting in /about#team
this.$router.push({ path: '/about', hash: '#team' })
reference:
https://router.vuejs.org/guide/essentials/navigation.html#navigate-to-a-different-location
To navigate to a different URL, use router.push. This method pushes a new entry into the history stack, so when the user clicks the browser back button they will be taken to the previous URL.
What you are trying to accomplish is not conform with the browser (history etc.) or
http protocol (GET/POST).
Also, when using path params and other variables, such will be ignored, as per the documentation.
Note: params are ignored if a path is provided, which is not the case for query, as shown in the example above. Instead, you need to provide the name of the route or manually specify the whole path with any parameter.
Using props here is very likely the wrong approach, as you will never get that data to the component.
I'm looking for the most optimal way of solving the following problem and would really appreciate some help. I have built a react native app which uses redux-saga for state management and redux-persist to keep offline data.
Problem:
When offline, users need to be able to use the native app to create "Posts" (for the sake of example) which can have multiple images attached to them. Then once they have internet connection they need to be able to click a sync/upload button. This button changes state.offlineQueue.offlineQueueShoud from 'cache' to 'sync'
Few things to consider; server side, I have a posts table, and an images table with a many to one relationship (many images to one post), which means to upload an image to the server I need to pass the post_id; meaning I have to have uploaded the post it's 'attached' to to the server so I can pass the post_id in the request. To solve this part, I have a function that uses temporary uuid's to maintain the relationship between posts and images:
function* postProcessToOfflineQueueSaga (action) {
try {
let post = Object.assign({}, action.payload);
post.uuid = uuid();
post.uploaded = false;
const imagesArr = post.images;
imagesArr.forEach(image => {
image.uuid = uuid();
image.postUuid = post.uuid;
});
post.imageIds = imagesArr.map(image => image.uuid);
delete post.images;
yield put({ type: POST_ADD_TO_OFFLINE_QUEUE, post });
yield put({ type: IMAGE_ADD_TO_OFFLINE_QUEUE, imagesArr });
} catch (error) {
console.log(error)
}
}
Which then saves it to the app state into two arrays; posts and images. E.g.
state.offlineQueue.offlinePosts: [
...
{
id: undefined,
uuid: "4df64ee5-29ba-4347-ae30-ee3d5602eae4",
imageIds: [
"62e11ef4-01f7-4052-a3e4-6cd109392818",
"2c7065ef-fed9-457f-950a-08d4224516dd",
],
uploaded: false,
}
...
]
state.offlineQueue.offlineImages: [
...
{
id: undefined,
uuid: "62e11ef4-01f7-4052-a3e4-6cd109392818",
postId: undefined,
postUuid: "4df64ee5-29ba-4347-ae30-ee3d5602eae4",
uploaded: false,
uri: "/path/to/file/on/device",
},
{
id: undefined,
uuid: "2c7065ef-fed9-457f-950a-08d4224516dd",
postId: undefined,
postUuid: "4df64ee5-29ba-4347-ae30-ee3d5602eae4",
uploaded: false,
uri: "/path/to/file/on/device",
},
...
]
state.offlineQueue.offlineQueueShoud: 'cache' // either 'cache' or 'sync'
So how do I go about sending this data to the server? What I'm thinking is:
Check 'offlineQueueShoud' (if 'cache' don't do anything to save battery?)
If offlineQueueShoud === 'sync', first iterate through the posts array and send each post to the server and use the response so that we can set post.id and image.postId to the server generated id.
Once all posts uploaded, start uploading images one by one as we now have the right post id.
Once all posts and images uploaded, clear the list.
I've had a look at redux saga channels, is that the best way to do it? If so, how do I make it so that if offlineQueueShoud === 'cache' it doesn't eat up battery, and if the app is closed/reopened no data is lost. Apologies if I'm being a noob, I'm only young :)
P.S. am I even doing this all the right way?!
Here's the flow of how my end-product should work:
When the user opens the app for the first time, fetch all the data
i.e., including images(150+) and relevant JSON objects.
On opening the app subsequently, the images and data should load
from local storage i.e., no need for internet at all.
I know it seems weird but this is my use case:
The product is a Wayfinder running on Android Box(55-inch touchscreen TV ) which will be placed in the shopping mall. It will not have access to the internet unless I manually connect it.
Hence it should load the data when opening for the first time i.e. when I'm configuring the application.
Solutions I have come across:
Realm: Local database management with excellent support for react-native - my option right now
Native Async Storage: Not suitable for large data
SQLite: Not comfortable with SQL queries
I'm still looking for options on how differently this problem can be tackled. Also, I'm familiar with Redux.
Thanks.
Check out react-native-fs (or expo-file-system if working with expo).
It is specially designed to store files on the device. In your component, it would look something like this:
const RNFS = require('react-native-fs');
RNFS
.downloadFile({ fromUrl: myURL, toFile: myFilePath })
.promise
.then(res => console.log('Done'));
use pouchDB database , this is work with indexDB local browser database
call XHR request for image and convert response to binary data and store in local database
when need to preview image , get from database and make a blobUrl and show in img tag
axios.get(url, {
progress: false, responseType: 'arraybuffer',
onDownloadProgress: (progressEvent) => {
precent = (100 * progressEvent.loaded / progressEvent.total)
console.log(precent)
}
})
.then(resp => {
//get db
let db = $db.dbModel
//set attach
db.get(doc._id).then((doc) => {
db.putAttachment(doc._id, 'index.mp4', doc._rev, new Blob([new Uint8Array(resp.data)], {type: 'video/mp4'}), 'video/mp4')
.then(res => {
// console.log('success store file')
})
})
})
https://github.com/mohammadnazari110/pwa_offline_video_download
I'm using serverless and https://github.com/horike37/serverless-step-functions to try and implement a system that is hit by a user, returns HTML based on a database entry for the params provided and then moves to a second function that writes to the database (without forcing the user to wait).
I think a step function in the right approach but I can't seem to get it to return HTML - it always returns a JSON body with the executionArn and startDate. e.g.
{
"executionArn": "arn:aws:states:us-west-2:.......etc...",
"startDate": 1513831673.779
}
Is it possible to have my html body return? At the moment my lambda function returns a simple h1 tag:
'use strict';
module.exports.requestHandler = (event, context, callback) => {
const response = {
statusCode: 200,
headers: {
'Content-Type': 'text/html'
},
body: `<h1>Success!</h1>`,
};
callback(null, response);
};
This is the state machine I'm aiming to create.
I would suggest going for a react/angular/vue frontend hosted e.g. on S3/CDN that uses serverless for backend queries only, instead of rendering dynamic HTML through Lambdas. The 'standard' approach allows you to build apps that are much more responsive and can benefit from e.g. CDNs.
See e.g. https://www.slideshare.net/mitocgroup/serverless-microservices-real-life-story-of-a-web-app-that-uses-angularjs-aws-lambda-and-more or https://serverless-stack.com/