I am trying to upload an image file to my backend. However no matter the device (Android or IOS) I am getting a 400 error code. Don't know what I am doing wrong but i follow the documentation on #nativescript/background-http for uploading files
Nativescript Version: 7
Angular Version: 10
Issue on Both Android and IOS
CONSOLE LOG:
shared.service.ts:48 File exists: true
shared.service.ts:54 photo Saved: true
Photo File: {
"_path": "/data/user/0/org.nativescript.WorkoutTracker/files/Stone0.png",
"_name": "Stone0.png",
"_extension": ".png"
}
shared.service.ts:164 upload progress: 0.1%
shared.service.ts:164 upload progress: 100.0%
profile.component.ts:83
Server error: {
"eventName": "error",
"object": {
"_observers": {
"progress": [
{}
],
"error": [
{}
],
"complete": [
{}
]
},
"_session": {
"_id": "img_upload"
},
"_id": "img_upload{1}",
"_description": "Uploading",
"_upload": 120143,
"_totalUpload": 120143,
"_status": "error"
},
"error": null,
"responseCode": 400,
"response": {}
}
This is the code:
imageUpload(photo: File, token: string) {
let observer: Subscriber<Image>;
const imageUpload$ = new Observable<Image>(
(observ) => (observer = observ)
);
const imgUrl = apiDomain + images;
console.log("Filee exists:", File.exists(photo.path));
const params = [];
const param = {
name: "photo",
filename: photo.path,
mimeType: "image/jpeg",
};
params.push(param);
const headers = {
// "Content-Type": "application/protobuf",
'Authorization': `Bearer ${token}`,
"Content-Type": "application/octet-stream",
// 'Accept': 'application/protobuf',
// "File-Name": photo.name
};
// const headers = new HttpHeaders({
// Authorization: "Bearer " + token,
// // 'Accept': 'application/protobuf',
// "Content-Type": "application/protobuf",
// // "Content-Type": "application/octet-stream",
// });
// console.log("Content-Type:", headers);
this.fileUpload<Image>(imgUrl, { requestType: "POST", headers }, params).subscribe(
(res) => {
if (res instanceof Image) {
observer.next(res);
}
},
(err) => {
observer.error(err);
}
);
return imageUpload$;
}
fileUpload<E>(uri: string, body: { requestType?: "POST" | "GET", headers}, params: any[]) {
let observer: Subscriber<E | ProgressEventData | ResultEventData>;
const request$ = new Observable<E | ProgressEventData | ResultEventData>((observ) =>(observer = observ));
const reqSession = session("file-upload");
const request = {
url: uri,
method: body.requestType ?? "POST",
description: "Uploading",
headers: body.headers,
};
console.log("request", request);
console.log("params", params);
const task = reqSession.multipartUpload(params, request);
task.on("progress", (evt) => {
console.log(
"upload progress: " +
((evt.currentBytes / evt.totalBytes) * 100).toFixed(1) +
"%"
);
observer.next(evt);
});
task.on("error", (evt) => {
console.log("upload error");
observer.error(evt);
});
task.on("complete", (evt) => {
const event: any = evt;
if (global.isIOS) {
if (event.responseCode >= 200 && event.responseCode < 300) {
console.log("success", event);
const object: E = event.object;
observer.next(object);
observer.complete();
} else if (
event.responseCode >= 400 &&
event.responseCode < 500
) {
const errorResp: ErrorEventData = event;
observer.error(errorResp);
}
} else if (global.isAndroid) {
console.log("success", event.responseCode, event);
const object: E = event.object;
observer.next(object);
observer.complete();
}
});
return request$;
}
The 400 error was due to the name in the params for me
const param = {
name: "photo", // This needed to match the name in the backend
filename: photo.path,
mimeType: "image/jpeg",
};
Related
hi I have one endpoint which is pass multipart formdata
URL : http://100.20.168.179/public/index.php/maintenances/create_ticket
Method: Post
Body request
const SelectData = {
"description": "Fff",
"room_id": "Ghh",
"maintenance_unique_id": "1662630778728",
"lang_flag": "en",
"asset_type": "2",
"longitude": "0.0",
"work_type": "69",
"user_id": "20",
"latitude": "0.0",
"area": "291",
"location": "22",
"urgency_level": "4",
"category_name": "",
"device_id": "2",
"captured_adress": "3377",
"reported_on": "2022-09-08 03:22:58",
"is_mediafile": "0"
}
My code as below
const form = new FormData();
const imageFileData = {
name: imageFilePath?.fileName,
type: `image/jpg`,
uri: imageFilePath?.uri,
};
form.append('webdata', JSON.stringify(SelectData));
if (imageFilePath?.uri || videoFilePath?.uri ) {
form.append('file_name', imageFileData );
}
else{
form.append('file_name', JSON.stringify(null));
}
addTicket(Config.BASE_URL + '/maintenances/create_ticket',form);
useAddTicket.ts
const useAddTicket = () => {
// const [data, setData] = useState();
const [isLoading, setIsLoading] = useState(false);
const navigation = useNavigation();
const addTicket = async (url: string, data: any) => {
console.log('formDatain Hook', data);
console.log('url Hook', url);
console.log('internet', globals.GlobalVariable.isConnected);
if (globals.GlobalVariable.isConnected === true) {
try {
setIsLoading(true);
const headers = {
'Content-Type': 'multipart/form-data; boundary=V2ymHFg03ehbqgZCaKO6jy',
// Connection: 'keep-alive',
// 'Content-Disposition': 'form-data; name="webdata"',
};
const response = await axios.post(url, data, { headers: headers });
if (response.data.sStatus == 1) {
setIsLoading(false)
console.log('useAddTicket Data res -->', response);
Alert.alert(`${response.data.sData.maintenance_id}`, response.data.sMessage, [
{ text: 'OK', onPress: () => navigation.goBack() },
]);
}
} catch (error) {
console.log('useAddTicket error -->', error);
setIsLoading(false);
}
} else {
Alert.alert('No Internet!');
}
};
return {
isLoading,
// data,
addTicket,
};
};
export default useAddTicket;
Issue is Above code working in iOS emulator but in Android it is not working in emulator as well as Real device . When i try to run in android it is continuously loading API call is not happened so any idea how can I solve this ? Your all suggestions is appreciated
NOTE: I mage getting log till internet true inside addTicket function. It means my request is not reach to Endpoint
Try as below:
const oFormData = new FormData();
oFormData.append("image", {
uri: val.uri,
type: val.type,
name: val.fileName
});
return axios.post(postUrl, oFormData);
Hi There I am trying send Image (Buffer data) and Some string using formdata to node js and mongo db using expo react native.But some how I am not able to send data using front end however my code works fine with Post man.I am sharing my code below and also sharing my error.My error shows data in console in error block but doesnot post it to database here is my front end code:
frontend.js
export default class Sellnow extends Component {
constructor(props) {
super(props);
this.onChangePetName = this.onChangePetName.bind(this);
this.onChangePetTitle = this.onChangePetTitle.bind(this);
this.onChangePetContact = this.onChangePetContact.bind(this);
this.onChangePetPrice = this.onChangePetPrice.bind(this);
this.onChangePetDescription = this.onChangePetDescription.bind(this);
this.onValueChangeCat= this.onValueChangeCat.bind(this);
this.onValueChangeCity= this.onValueChangeCity.bind(this);
this.onFileChange = this.onFileChange.bind(this);
this.onSubmit = this.onSubmit.bind(this);
this.state = {
name: "",
title: "",
contact: "",
price: "",
description: "",
selectedcat:"",
selectedcity:"",
imgforsell:"",
category: [
{
itemName: "Select Category...."
},
{
itemName: "Pets Food"
},
{
itemName: "Pets Products"
},
{
itemName: "Pets Accessories"
}
],
cityCategory:[
{
itemName: "Select City...."
},
{
itemName: "Islamabad"
},
{
itemName: "Rawalpindi"
},
{
itemName: "Lahore"
},
{
itemName: "Peshawar"
},
{
itemName: "Karachi"
},
{
itemName: "Quetta"
}
]
};
}
onChangePetName(e) {
this.setState({ name: e.target.value });
}
onChangePetTitle(e) {
this.setState({ title: e.target.value });
}
onChangePetContact(e) {
this.setState({ contact: e.target.value });
}
onChangePetPrice(e) {
this.setState({ price: e.target.value });
}
onChangePetDescription(e) {
this.setState({ description: e.target.value });
}
// categories function
onValueChangeCat(e) {
this.setState({ selectedcat: e.targetvalue })
}
// city function
onValueChangeCity(e) {
this.setState({ selectedcity: e.targetvalue })
}
onFileChange(e) {
this.setState({ imgforsell: e.targetvalue})}
// uploading Image
_getPhotoLibrary = async () => {
let result = await ImagePicker.launchImageLibraryAsync({
allowsEditing: true,
base64: true,
exif: true,
aspect: [4, 3]
});
if (!result.cancelled) {
this.setState({ imgforsell: result });
}
this.props.navigation.setParams({
imgforsell: this.state.imgforsell
});
};
async onSubmit() {
const FormData = global.FormData;
const formData = new FormData();
formData.append("name", this.state.name);
formData.append("title", this.state.title);
formData.append("contact", this.state.contact);
formData.append("price", this.state.price);
formData.append("description", this.state.description);
formData.append("selectedcat", this.state.selectedcat);
formData.append("selectedcity", this.state.selectedcity);
formData.append("imgforsell",this.state.imgforsell)
axios
.postForm(
`http://192.168.88.45:4040/pets/addpets `,
QueryString.stringify({formData}),
{
headers: {
'Content-Type': 'multipart/form-data',
'Accept': 'application/json'
},
},
)
.then(({ data }) => {
console.log(data);
})
.catch((err) => {
console.error(err.toJSON());
})
/*.finally(() => {
this.setState({
name: "",
title: "",
contact: "",
price: "",
description: "",
selectedcat: "",
selectedcity: "",
imgforsell: "",
});
});*/
}
render() {
const {imgforsell} = this.state
Here is the error:
>
> Object {
"code": "ERR_BAD_REQUEST",
"columnNumber": undefined,
"config": Object {
"adapter": [Function xhrAdapter],
"data": "formData%5B_parts%5D%5B0%5D%5B0%5D=name&formData%5B_parts%5D%5B0%5D%5B1%5D=Dummy&formData%5B_parts%5D%5B1%5D%5B0%5D=title&formData%5B_parts%5D%5B1%5D%5B1%5D=Dummy&formData%5B_parts%5D%5B2%5D%5B0%5D=contact&formData%5B_parts%5D%5B2%5D%5B1%5D=12345678900&formData%5B_parts%5D%5B3%5D%5B0%5D=price&formData%5B_parts%5D%5B3%5D%5B1%5D=1234567&formData%5B_parts%5D%5B4%5D%5B0%5D=description&formData%5B_parts%5D%5B4%5D%5B1%5D=Qwerty%20keypad&formData%5B_parts%5D%5B5%5D%5B0%5D=selectedcat&formData%5B_parts%5D%5B5%5D%5B1%5D=Pets%20Products&formData%5B_parts%5D%5B6%5D%5B0%5D=selectedcity&formData%5B_parts%5D%5B6%5D%5B1%5D=Peshawar&formData%5B_parts%5D%5B7%5D%5B0%5D=imgforsell&formData%5B_parts%5D%5B7%5D%5B1%5D%5Bcancelled%5D=false&formData%5B_parts%5D%5B7%5D%5B1%5D%5Bwidth%5D=2160&formData%5B_parts%5D%5B7%5D%5B1%5D%5Bexif%5D%5BDateTime%5D=2015%3A11%3A04%2017%3A32%3A48&formData%5B_parts%5D%5B7%5D%5B1%5D%5Bexif%5D%5BSoftware%5D=Adobe%20Photoshop%20CC%20%28Windows%29&formData%5B_parts%5D%5B7%5D%5B1%5D%5Bexif%5D%5BXResolution%5D=72&formData%5B_parts%5D%5B7%5D%5B1%5D%5Bexif%5D%5BImageWidth%5D=2160&formData%5B_parts%5D%5B7%5D%5B1%5D%5Bexif%5D%5BOrientation%5D=0&formData%5B_parts%5D%5B7%5D%5B1%5D%5Bexif%5D%5BImageLength%5D=1620&formData%5B_parts%5D%5B7%5D%5B1%5D%5Bexif%5D%5BResolutionUnit%5D=2&formData%5B_parts%5D%5B7%5D%5B1%5D%5Bexif%5D%5BLightSource%5D=0&formData%5B_parts%5D%5B7%5D%5B1%5D%5Bexif%5D%5BColorSpace%5D=1&formData%5B_parts%5D%5B7%5D%5B1%5D%5Bexif%5D%5BJPEGInterchangeFormat%5D=302&formData%5B_parts%5D%5B7%5D%5B1%5D%5Bexif%5D%5BYResolution%5D=72&formData%5B_parts%5D%5B7%5D%5B1%5D%5Bexif%5D%5BCompression%5D=6&formData%5B_parts%5D%5B7%5D%5B1%5D%5Bexif%5D%5BJPEGInterchangeFormatLength%5D=5674&formData%5B_parts%5D%5B7%5D%5B1%5D%5Bheight%5D=1620&formData%5B_parts%5D%5B7%5D%5B1%5D%5Bbase64%5D=%2F9j%2F4QG%2BRXhpZgAATU0AKgAAAAgADAESAAQAAAABAAAAAAEAAAQAAAABAAAIcAEaAAUAAAABAAAAngExAAIAAAAdAAAApgICAAQAAAABAAAWKodpAAQAAAABAAAA3wEDAAMAAAABAAYAAAEbAAUAAAABAAAAwwEBAAQAAAABAAAGVAEyAAIAAAAUAAAAywEoAAMAAAABAAIAAAIBAAQAAAABAAABLgAAAAAACvyAAAAnEEFkb2JlIFBob3Rvc2hvcCBDQyAoV2luZG93cykAAAr8gAAAJxAyMDE1OjExOjA0IDE3OjMyOjQ4AAACkggAAwAAAAEAAAAAoAEAAwAAAAEAAQAAAAAAAAAIARoABQAAAAEAAAFjATEAAgAAAB0AAAFrAgIABAAAAAEAABYqAQMAAwAAAAEABgAAARsABQAAAAEAAAGIATIAAgAAABQAAAGQASgAAwAAAAEAAgAAAgEABAAAAAEAAAEuAAAAAAAK%2FIAAACcQQWRvYmUgUGhvdG9zaG9wIENDIChXaW5kb3dzKQAACvyAAAAnEDIwMTU6MTE6MDQgMTc6MzI6NDgAAAEANwADAAAAAQABAAAAAAAA%2F%2BAAEEpGSUYAAQEAAAEAAQAA%2F9sAQwABAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEB%2F9sAQwEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEB%2F8AAEQgGVAhwAwEiAAIRAQMRAf%2FEAB8AAAEFAQEBAQEBAAAAAAAAAAABAgMEBQYHCAkKC%2F%2FEALUQAAIBAwMCBAMFBQQEAAABfQECAwAEEQUSITFBBhNRYQcicRQygZGhCCNCscEVUtHwJDNicoIJChYXGBkaJSYnKCkqNDU2Nzg5OkNERUZHSElKU1RVVldYWVpjZGVmZ2hpanN0dXZ3eHl6g4SFhoeIiYqSk5SVlpeYmZqio6Slpqeoqaqys7S1tre4ubrCw8TFxsfIycrS09TV1tfY2drh4uPk5ebn6Onq8fLz9PX29%2Fj5%2Bv%2FEAB8BAAMBAQEBAQEBAQEAAAAAAAABAgMEBQYHCAkKC%2F%2FEALURAAIBAgQEAwQHBQQEAAECdwABAgMRBAUhMQYSQVEHYXETIjKBCBRCkaGxwQkjM1LwFWJy0QoWJDThJfEXGBkaJicoKSo1Njc4OTpDREVGR0hJSlNUVVZXWFlaY2RlZmdoaWpzdHV2d3h5eoKDhIWGh4iJipKTlJWWl5iZmqKjpKWmp6ipqrKztLW2t7i5usLDxMXGx8jJytLT1NXW19jZ2uLj5OXm5%2Bjp6vLz9PX29%2Fj5%2Bv%2FaAAwDAQACEQMRAD8A%2FMk%2FearX%2FLP%2FAD%2FeqqfvNTfO%2Fd9f%2FHv9r619Bhf%2FAJA%2FMX0%2FwosUUVYoJK9WKKKD0AqxVepLfv8A9s%2F%2FAGpQBNH97%2FP%2FAE0oP3mqxH97%2FP8A00oP3mrorHnke5fX9DVjcvr%2BhqP7Mv8Ad%2F8AHT%2FjVj7Mv93%2FAMdP%2BNcv1P8Axf1%2F26d913X3r%2FMmooorqOAh3N6%2FoKj8tv8AKD%2FCr37v%2FO6j93%2FndXP9V8vw%2FwDtSub%2B7H7v%2BCVSd3AHr3%2Bvr%2Fun%2FPWaAhOOp%2Fd5PI6Fsdj2%2FwDQucleTyNgwByep2eh9Dnt%2FkmkS38nJPTjA9eXHXORg4PQ5z1IJrfDYdJPq%2Bm%2FRy310t83dvdaNX6dOn3t%2Fj%2Flu7ss1H5Ht%2F45Rb9%2F%2B2f%2FALUqxb9%2F%2B2f%2FALUpiM%2FyPb%2FxyrA%2FcZ%2FzjGf97Ocn86kqPzvf%2FwAe%2FwDr10AWPM9v1%2F8ArUeZ7fr%2FAPWo8v3%2FAE%2F%2BvR5fv%2Bn%2FANegPa%2F3vw%2F4BcooornAjBD5B4PY8%2Bpz29FPX%2BfVqnZuGM9O%2Fp%2BdKVxkjp%2FLnHrk5%2Fz61ZHzgg9V7%2FU%2Bn0%2Bv50q2HTUu6t%2Bc7dev37K7s7NO11una%2Fyba%2FT8bphb9%2F8Atn%2F7UqSiimIKKjm%2Fi%2F4HUlAFfZ%2Fs%2FwDjv%2F1qk8z2%2FX%2F61Sb%2FAPb%2FAPHv%2Fsqk8v3%2FAE%2F%2BvXQHtf734f8AAKdWKr0UAWKsVHb9%2FwDtn%2F7UqSucAooqPzvf%2FwAe%2FwDr0AU9n%2Bz%2FAOO%2F%2FWo2f7P%2FAI7%2FAPWqxv8A9v8A8e%2F%2Byo3%2FAO3%2FAOPf%2FZV0B7X%2B9%2BH%2FAACO37%2F9s%2F8A2pUlFFBzkdv3%2FwC2f%2FtSpKjt%2B%2F8A2z%2F9qVJQdBJ5nt%2Bv%2FwBarHme36%2F%2FAFqr%2BX7%2FAKf%2FAF6seX7%2FAKf%2FAF6A9r%2Fe%2FD%2FgB5nt%2Bv8A9ajzPb9f%2FrVHv%2F2%2F%2FHv%2FALKjf%2Ft%2F%2BPf%2FAGVAe1%2Fvfh%2FwCxRVff8A7f8A49%2F9lUfl%2B%2F6f%2FXrnK%2BsS%2Fn%2F8lX%2FyJYD54A%2FX6%2Bo%2F2T%2FnqAhMgcnueR0Jx29Mf%2FrJpSue%2FwBOP%2Fr0iD5Tjjp83XPJHQnj7pH%2BPUrC4dJN21dr6u2jlvq9vvu3a60Z9Yl37aWXd635e2%2Fysr3I6sVXqTzvf%2Fx7%2FwCvXSSSUUUUAFFFFAFzyPb%2FAMcqOpPO9%2F8Ax7%2F69Hke3%2FjlBzkdWKj8j2%2F8cq5QBTghxu9eO3TlgOM9Tn8PqakqMTeRnvjHP4t29vTPfvu4koOgdsb0%2FUf41Y2N6fqP8aML%2Fe%2F8dP8AjUduF5%2Bb%2Fnn%2FAAn%2FAKae9c%2FsPP8AH%2F7Ur6xL%2Bf8A8lX%2FAMiWqKk8j2%2F8cqv5Ht%2F45QSN2N6fqP8AGjY3p%2Bo%2Fxo3N6%2FoKNzev6Cj2Hn%2BP%2FwBqA2o%2FI9v%2FAByrlR%2BR7f8Ajlc56BX8j2%2F8cqSpPI9v%2FHKuUAV6Kj8j2%2F8AHKkoAKKKKALWxvT9R%2FjRsb0%2FUf40bm9f0FG5vX9BXR7fy%2FD%2FAO2PPAwfK3H%2FAI5%2FtVHH93%2FP96SrB%2B63%2Bf4qI%2Fu%2F5%2FvSVy4vr%2FiX%2FuQ74%2FCvRf8AuQo1J5Ht%2FwCOUeR7f%2BOVcqhlPyPb%2FwAcqSrFFABRUdv3%2FwC2f%2FtSrlABRUfke3%2FjlSUAR%2BR7f%2BOVcoooAj8j2%2F8AHKPI9v8AxyrlFABUfke3%2FjlHke3%2FAI5VygCn5Ht%2F45VyiigAqPyPb%2FxyjyPb%2FwAcq5QBT8j2%2FwDHKPI9v%2FHKuUUAR%2BR7f%2BOUeR7f%2BOVcooAp%2BR7f%2BOUeR7f%2BOVcooAr1YqxRQBXqPyPb%2FwAcq5RQBXoqxRQBXqxRUnke3%2FjlAEdR%2BR7f%2BOVY8j2%2F8cqSgCvViirFAFPyPb%2FxyrHke3%2FjlA%2FfZ%2FznO76Y6H9OTgZseR7f%2BOUAR1H5Ht%2F45VyigAqPyPb%2FAMcqx5Ht%2FwCOVJQBT8j2%2FwDHKuVYqPyPb%2FxygCSo%2FI9v%2FHKseR7f%2BOVJQBH%2FAKN%2FnFHke3%2FjlXKKAI%2FI9v8AxyrHke3%2FAI5VjyPb%2FwAcqSgAqTyPb%2FxyrHke3%2FjlSV54Efke3%2FjlHke3%2FjlXKjH7jP8AnGM%2F72c5P50AUY4Pm6f%2BOf8AXSnVaj%2B9%2Fn%2FppUMEON3rx26csBxnqc%2Fh9TVL4an%2FAG5%2F6UY1vh%2Fr%2BYPI9v8AxypKueZ7fr%2F9arHme36%2F%2FWo5JdvxX%2BZ1fWX%2FAHf%2FAAGX%2FwAkU6j8j2%2F8crQ8z2%2FX%2FwCtUmz%2FAGf%2FAB3%2FAOtRyS7fiv8AMPrL%2Fu%2F%2BAy%2F%2BSKcEON3rx26csBxnqc%2Fh9TR9i%2Fzt%2FwDrVoeR7f8AjlHke3%2FjlSZlfyPb%2FwAcqx5Ht%2F45VzZ%2Fs%2F8Ajv8A9ajZ%2Fs%2F%2BO%2F8A1qrkl2%2FFf5mn1l%2F3f%2FAZf%2FJFPyPb%2FwAco%2Bxf52%2F%2FAFq1Nn%2Bz%2FwCO%2FwD1qsbP9n%2Fx3%2F61HJLt%2BK%2FzD6y%2F7v8A4DL%2FAOSMyCHG7147dOWA4z1Ofw%2Bpo8m19vzNXxD5%2Be3T%2BbD179fw6jGaseR7f%2BOVJ2FDybX2%2FM1P5Ht%2F45Wh5Ht%2F45UlAFPyPb%2FxyrH2L%2FO3%2FwCtR5Ht%2FwCOVqUAZfke3%2FjlAh8%2FPbp%2FNh69%2Bv4dRjNaHke3%2FjlSUAU%2FI9v%2FAByrH2L%2FADt%2F%2BtVjyPb%2FAMcqSgCn5Ht%2F45VypPI9v%2FHKPI9v%2FHKAK%2Fke3%2FjlHke3%2FjlaHke3%2FjlHke3%2FAI5QBB5Nr7fmafV2CHG7147dOWA4z1Ofw%2Bpp9AFTybX2%2FM0eTa%2B35mtCCHG7147dOWA4z1Ofw%2BppPI9v%2FHKAM%2F7Hben%2FAI8KPsdt6f8AjwrQ8j2%2F8cqx5Ht%2F45QBQ8m19vzNHk2vt%2BZq%2FwCR7f8AjlHke3%2FjlAGf5Ht%2F45Vj7F%2Fnb%2F8AWqx5Ht%2F45VjyPb%2FxygCh5Nr7fmaTyPb%2FAMcrZghxu9eO3TlgOM9Tn8PqaTyPb%2FxygDH8j2%2F8cpfJtfb8zWv5Ht%2F45UlAGZ5Nr7fmaTyPb%2FxytDyPb%2FxyjyPb%2FwAcoAz%2FACPb%2FwAco8j2%2FwDHK1Kj8j2%2F8coAoeTa%2B35mk8j2%2FwDHK0PI9v8AxyjyPb%2FxygCh5Nr7fmaTyPb%2FAMcrUooAzPJtfb8zVurnke3%2FAI5QIfIzznGO3u49e2Afox5OaAK%2Fke3%2FAI5R5Ht%2F45VjyPb%2FAMcqx5Ht%2FwCOUAQeTa%2B35mk8j2%2F8crUqS37%2FAPbP%2FwBqUAUIIcbvXjt05YDjPU5%2FD6mk8j2%2F8crUqPyPb%2FxygCDybX2%2FM0eTa%2B35mr4h8jPOcY7e7j17YB%2BjHk5o8j2%2F8coAz%2FI9v%2FHKseR7f%2BOVoeR7f%2BOUeR7f%2BOUAZ%2Fke3%2FjlLBDjd68dunLAcZ6nP4fU1p1H5Ht%2F45QBnyw9cf8A6%2BXzwT%2Fs9O%2BRz8uCeR7f%2BOVoCHz89un82Hr36%2Fh1GM0eR7f%2BOUAUPJtfb8zR5Nr7fma06KAKfke3%2FjlHke3%2FAI5Wh5Ht%2FwCOUeR7f%2BOUAV%2FI9v8AxyjyPb%2FxyrHke3%2FjlHke3%2FjlAFf7F%2Fnb%2FwDWpfJtfb8zWnRQBmeTa%2B35mjybX2%2FM1f8AI9v%2FABypKAMP7Hben%2Fjwo%2Bx23p%2F48K2PsX%2Bdv%2F1qr%2BR7f%2BOUAY%2Fke3%2FjlHke3%2FjlbHke3%2FjlV%2FI9v%2FHKAMfyPb%2FxyjyPb%2FxytjyPb%2Fxyq%2Fke3%2FjlAGf5Ht%2F45S%2BTa%2B35mtOo%2FI9v%2FHKAMjybX2%2FM0nke3%2FjlbHke3%2FjlV%2FI9v%2FHKAMfyPb%2FxyjyPb%2FxytjyPb%2Fxyq%2Fke3%2FjlAGP5Ht%2F45R5Ht%2F45Wx5Ht%2F45VfyPb%2FxygDLqOWHrj%2F8AXy%2BeCf8AZ6d8jn5cHQl%2FcZ7ev6465x07Zzkdc1X8j2%2F8coPPM%2FyPb%2Fxyl8m19vzNX%2FI9v%2FHKr%2BR7f%2BOV6AGf5Ht%2F45R5Ht%2F45WpVOWHrj%2F8AXy%2BeCf8AZ6d8jn5cEAz%2FACPb%2FwAcqv5Ht%2F45WgIfIzznGO3u49e2Afox5OaPI9v%2FABygDH8j732f2zjjPLDuT7E9ewyTuNV%2FI9v%2FABytjyPb%2FwAcqv5Ht%2F45QBQ8m19vzNPrQqPyPb%2FxygCh5Nr7fman8j2%2F8cq5Unke3%2FjlAGfb9%2F8Atn%2F7Uo8j2%2F8AHK0YIcbvXjt05YDjPU5%2FD6mk8j2%2F8coAz%2FI9v%2FHKWCHG7147dOWA4z1Ofw%2Bpq%2F5Ht%2F45RLD1x%2F8Ar5fPBP8As9O%2BRz8uCAZ%2Fke3%2FAI5Udanke3%2FjlHke3%2FjlAGP5Ht%2F45VfyPb%2FxytjyPb%2Fxyib%2BL%2FgdAGf5Ht%2F45R5Ht%2F45VjyPb%2FxyjyPb%2FwAcoAz%2FACPb%2FwAco%2Bxf52%2F%2FAFq1Kj8j2%2F8AHKAM%2FwAj2%2F8AHKPI9v8AxytDyPb%2FAMcqSgDL8j2%2F8cqv5Ht%2F45Wx5Ht%2F45R5Ht%2F45QBl1H9i%2FwA7f%2FrVseR7f%2BOVX8j2%2FwDHKAM%2FyPb%2FAMco8j2%2F8crUqPyPb%2FxygDP8j2%2F8co8j2%2F8AHK0PI9v%2FAByjyPb%2FAMcoAx%2FI9v8AxyrHke3%2FAI5Wh5Ht%2FwCOUeR7f%2BOUAZ8sPXH%2FAOvl88E%2F7PTvkc%2FLgn2L%2FO3%2FAOtWh5Ht%2FwCOUeR7f%2BOUAZ%2Fke3%2FjlAh8jPOcY7e7j17YB%2BjHk5rQ8j2%2F8co8j2%2F8coAp0VqeR7f%2BOUeR7f8AjlAH4%2Bn7zVNBDiNvXjt0%2BdgOM9Tn8PqahP3mrS%2F5Z%2F5%2FvUYX%2FwCQOF9P8KJKKr1Jb9%2F%2B2f8A7UroJLlV6sUUAUdjen6j%2FGrGxvT9R%2FjRub1%2FQVY3N6%2FoKPYef4%2F%2FAGoDaKKK6ANCio7fv%2F2z%2FwDalXK5wK9Sed7%2FAPj3%2FwBeo6sV0HOR%2Bd7%2FAPj3%2FwBepKj8j2%2F8cq5QBGP32f8AOc7vpjof05OBmSirFAFO37%2F9s%2F8A2pVyiigCvRVirFAFeirFV6ALFV6KKACrFV6sUAWKKr0UAWKr0UUAFFFWKAK9FFWKACiiigCxVeirFAFeirFV6ACiiigAooooAKKKkH77P%2Bc53fTHQ%2FpycDIAW%2Ff%2FALZ%2F%2B1KkoooAKKKKACox%2B%2Bz%2FAJznd9MdD%2BnJwMyVYoAj8j2%2F8cqOrFWKAK9FWKj8j2%2F8coAPI9v%2FAByiCHG7147dOWA4z1Ofw%2Bpqx5Ht%2FwCOUQQ43evHbpywHGepz%2BH1NAB5Ht%2F45VypIIcbvXjt05YDjPU5%2FD6mjyPb%2FwAcoAp1J5Ht%2FwCOVoQQ43evHbpywHGepz%2BH1NWPI9v%2FABygDH8j2%2F8AHKPI9v8AxytDyPb%2FAMco8j2%2F8coAjoqPyPb%2FAMcqSgAoqxVegCPyPb%2FxyjyPb%2FxyrlR%2BR7f%2BOUAXKp%2BR7f8AjlXKK5zoM37M393%2FAMdH%2BNH2Zv7v%2Fjo%2FxrQ8tv8AKD%2FCpNzev6Cj2Hn%2BP%2F2oGX9mb%2B7%2FAOOj%2FGpNjen6j%2FGtDc3r%2BgqOZm%2Bbn%2B%2F2FHsPP8f%2FALUBv%2FLP%2FP8AeqrH9...(truncated to the first 10000 characters)
at node_modules\react-native\Libraries\LogBox\LogBox.js:149:8 in registerError
at node_modules\react-native\Libraries\LogBox\LogBox.js:60:8 in errorImpl
at node_modules\react-native\Libraries\LogBox\LogBox.js:34:4 in console.error
at node_modules\expo\build\environment\react-native-logs.fx.js:27:4 in error
at node_modules\react-native\node_modules\promise\setimmediate\core.js:37:13 in tryCallOne
at node_modules\react-native\node_modules\promise\setimmediate\core.js:123:24 in setImmediate$argument_0
at node_modules\react-native\Libraries\Core\Timers\JSTimers.js:123:14 in _callTimer
at node_modules\react-native\Libraries\Core\Timers\JSTimers.js:177:14 in _callImmediatesPass
at node_modules\react-native\Libraries\Core\Timers\JSTimers.js:437:30 in callImmediates
at node_modules\react-native\Libraries\BatchedBridge\MessageQueue.js:388:6 in __callImmediates
at node_modules\react-native\Libraries\BatchedBridge\MessageQueue.js:365:10 in __guard
at node_modules\react-native\Libraries\BatchedBridge\MessageQueue.js:112:4 in callFunctionReturnFlushedQueue
here is the screen shot of post man:-
Blockquote
I guess you are sending a image in formData but you have to add type: 'image/jpeg', to the file attribute of the formData to fixed this
formData.append("imgforsell",this.state.imgforsell)
change with this
formData.append('imgforsell', {
uri: "file://" //Your Image File Path
type: 'image/jpeg',
name: 'imageName'
})
Visit Here your more doubts will be clear and you will find out how to do it in Ios and Android
I developed a mobile app to help sharing things. The user has to give infos about what he is sending and he can add a picture of the object. So i used the cordova file, camera and fileTransfert plugins. It worked fine on most of the devices i tested on, but i discovered that in some other phone, it doesn't. While doing some tests and research on one of those phones, i discovered that the upload() method of FileTransfert i use to send images to online server seems like not able to reach the folder where the image is stored. Here is a sample of my code. Would you please help me to confirm if i am rigth and how to make those phones to be able to post pictures on the platform?
public presentActionSheet(picture) {
if(this.translateService.currentLang=='fr'){
let actionSheet = this.actionSheetCtrl.create({
title: 'Quelle est la source?',
buttons: [
{
icon: 'images',
text: 'Mon téléphone',
handler: () => {
this.takePicture(this.camera.PictureSourceType.PHOTOLIBRARY, picture);
}
},
{
icon: 'camera',
text: 'Ma Camera',
handler: () => {
this.takePicture(this.camera.PictureSourceType.CAMERA, picture);
}
},
{
text: 'Annuler',
role: 'cancel'
}
]
});
actionSheet.present();
}else{
let actionSheet = this.actionSheetCtrl.create({
title: 'What is the source?',
buttons: [
{
icon: 'images',
text: 'My Phone',
handler: () => {
this.takePicture(this.camera.PictureSourceType.PHOTOLIBRARY, picture);
}
},
{
icon: 'camera',
text: 'My Camera',
handler: () => {
this.takePicture(this.camera.PictureSourceType.CAMERA, picture);
}
},
{
text: 'Cancel',
role: 'cancel'
}
]
});
actionSheet.present();
}
};
presentToast(message_error) {
let toast = this.toastCtrl.create({
message: message_error,
cssClass: 'alert-box',
position: 'middle',
showCloseButton: true,
closeButtonText: "OK"
});
toast.present();
}
//Here is the function to take a picture
public takePicture(sourceType, picture) {
// Create options for the Camera Dialog
var options = {
quality: 100,
sourceType: sourceType,
saveToPhotoAlbum: false,
correctOrientation: true
};
// Get the data of an image
this.camera.getPicture(options).then((imagePath) => {
// Special handling for Android library
if (this.platform.is('android') && sourceType === this.camera.PictureSourceType.PHOTOLIBRARY) {
this.filePath.resolveNativePath(imagePath)
.then(filePath => {
let correctPath = filePath.substr(0, filePath.lastIndexOf('/') + 1);
let currentName = imagePath.substring(imagePath.lastIndexOf('/') + 1, imagePath.lastIndexOf('?'));
this.copyFileToLocalDir(correctPath, currentName, this.createFileName(), picture);
});
} else {
console.log('In the else condition');
var currentName = imagePath.substr(imagePath.lastIndexOf('/') + 1);
var correctPath = imagePath.substr(0, imagePath.lastIndexOf('/') + 1);
this.copyFileToLocalDir(correctPath, currentName, this.createFileName(), picture);
}
}, (err) => {
if(this.translateService.currentLang=='fr'){
this.presentToast('Erreur, pas d\'image selectionnée.');
}else{
this.presentToast('Error, no image selected.');
}
});
}
// Create a new name for the image
private createFileName() {
var d = new Date(),
n = d.getTime(),
newFileName = n + ".jpg";
return newFileName;
}
// Copy the image to a local folder
//cordova.file.dataDirectory
private copyFileToLocalDir(namePath, currentName, newFileName, picture) {
this.file.copyFile(namePath, currentName, cordova.file.dataDirectory, newFileName).then(success => {
if(picture == "imageOne"){
this.mainImage = newFileName;
}else if(picture == "imageTwo"){
this.secondImage = newFileName;
}else{
this.thirdImage = newFileName;
}
//this.lastImage = newFileName;
}, error => {
if(this.translateService.currentLang=='fr'){
this.presentToast('Erreur, le fichier n\'a pas pu etre sauvegardé.');
}else{
this.presentToast('Error, file could not be saved.');
}
console.log(error);
});
}
// Always get the accurate path to your apps folder
public pathForImage(img) {
if (img === null) {
return '';
} else {
return cordova.file.dataDirectory + img;
}
}
public uploadImage(picture) {
// Destination URL
var url = "http://donation.oneclub1.org/donation-new/web/api/upload/image?context=donations";
// File for Upload
var targetPath: any;
if(picture == "imageOne"){
targetPath = this.pathForImage(this.mainImage);
}else if(picture == "imageTwo"){
targetPath = this.pathForImage(this.secondImage);
}else{
targetPath = this.pathForImage(this.thirdImage);
}
// File name only
var filename: any;
if(picture == "imageOne"){
filename = this.mainImage;
}else if(picture == "imageTwo"){
filename = this.secondImage;
}else{
filename = this.thirdImage;
}
var options = {
fileKey: "file",
fileName: filename,
chunkedMode: false,
mimeType: "multipart/form-data",
params : {'fileName': filename}
};
const fileTransfer: TransferObject = this.transfer.create();
// Use the FileTransfer to upload the image
return fileTransfer.upload(targetPath, url, options);/*.then(data => {
if(picture == "imageOne"){
this.mainImageLocal = parseInt(data.response);
}else if(picture == "imageTwo"){
this.secondImageLocal = parseInt(data.response);
}else{
this.thirdImageLocal = parseInt(data.response);
}
//this.presentToast('this is your image id'+this.mainImageLocal);
}, err => {
this.loading.dismissAll();
this.presentToast('Error while uploading file.');
})*/;
}
publish(){
if(this.mainImage!=null){
this.loading = this.loadingCtrl.create({
content: this.content2,
});
this.loading.present();
//var categoryId: number;
for(let parent of this.categories){
if(parent.name == this.asking_form_group.value.subcategory){
this.categoryId=parent.id;
console.log('Id found and it is:'+this.categoryId);
break;
};
};
//var userId: number;
if(localStorage.getItem('userId')){
this.userId= parseInt(localStorage.getItem('userId'));
console.log('got the user id in nmber:'+this.userId);
};
var headers = new Headers();
headers.append("Accept", 'application/json');
headers.append('Content-Type', 'application/json' );
let options = new RequestOptions({ headers: headers });
this.uploadImage('imageOne').then(data => {
this.mainImageLocal = parseInt(data.response);
this.postParams = {
name: this.asking_form_group.value.name,
category: this.categoryId,
description: this.asking_form_group.value.description,
image: this.mainImageLocal,
user: this.userId
}
this.http.post(this.Api+"/donations/requests?api_key="+localStorage.getItem('userApiKey'), this.postParams, options).map(res => res.json())
.subscribe(data => {
this.loading.dismissAll();
if(this.translateService.currentLang=='fr'){
this.presentToast('Félicitations!!Votre demande a été postée sur la plateforme!')
}else{
this.presentToast ('Congratulations !! Your request has been posted on the platform!')
}
this.events.publish('ask:posted', 1);
this.navCtrl.setRoot(Dashboard);
}, error => {
console.log(error);
//this.asking_form_group.reset();
this.testor = error.response;
this.loading.dismissAll();
this.presentToast(this.error);
});
});
}else{
this.loading = this.loadingCtrl.create({
content: this.content2,
});
this.loading.present();
//var categoryId: number;
for(let parent of this.categories){
if(parent.name == this.asking_form_group.value.subcategory){
this.categoryId=parent.id;
console.log('Id found and it is:'+this.categoryId);
break;
};
};
if(localStorage.getItem('userId')){
this.userId= parseInt(localStorage.getItem('userId'));
console.log('got the user id in nmber:'+this.userId);
};
var headers = new Headers();
headers.append("Accept", 'application/json');
headers.append('Content-Type', 'application/json' );
let options = new RequestOptions({ headers: headers });
this.postParams = {
name: this.asking_form_group.value.name,
category: this.categoryId,
description: this.asking_form_group.value.description,
image: this.mainImageLocal,
user: this.userId
}
this.http.post(this.Api+"/donations/requests?api_key="+localStorage.getItem('userApiKey'), this.postParams, options).map(res => res.json())
.subscribe(data => {
this.loading.dismissAll();
if(this.translateService.currentLang=='fr'){
this.presentToast('Félicitations!!Votre demande a été postée sur la plateforme!')
}else{
this.presentToast ('Congratulations !! Your request has been posted on the platform!')
}
this.events.publish('ask:posted', 1);
this.navCtrl.setRoot(Dashboard);
}, error => {
console.log(error);
//this.asking_form_group.reset();
this.testor = error.response;
this.loading.dismissAll();
this.presentToast(this.error);
});
};
}
Sorry i found what the issue was and i fogot to put it here. The problem was actually about filesize. Filetransfert default limit is 7.5Mo. Sending file greater than that would fail. In some phones, camera default configurations put the picture size to 8 or greater Mpx. So that why it could not work in those phones.
I have tried several times to send the data and receive a response, but it does not seem to be sending the data put in by the user. I have tried going about this in several ways,I will share the code for the last two.
ONE
state = {
phoneNo: '',
pin: '',
isLoggingIn: false,
message: ''
}
_userLogin = () => {
console.log("userLogin");
this.setState({isLoggingIn: true, message:''});
var params = {
phoneNo: this.state.phoneNo,
pin: this.state.pin
};
var proceed = false;
fetch("https://"+"<url>", {
method: "POST",
headers: {
'Accept': 'application/json',
'Content-Type': 'application/json'
},
body: JSON.stringify(params)
})
.then(
(response) => response.json())
.then((response) => {
if (response.status == 200) {
proceed = true;
}
else {
this.setState({ message: response.message });
console.log(message); }
})
.then(() => {
this.setState({ isLoggingIn: false })
if (proceed) this.props.onLoginPress();
})
.catch(err => {
console.log(err.message);
this.setState({ message: err.message });
this.setState({ isLoggingIn: false })
});
}
Two
The only difference here is how I am handling the response so I will only add that section. I thought that the issue might be due to syntax at this point.
.then(function(response){
return response.json();
})
.then(function(data){
console.log(data)
I have been through various tutorials, github and stackoverflow pages addressing the issue but I seem to be missing something. I keep getting a JSON parse error and I am convinced that perhaps the data is never being sent to the url because I get the error regardless of user input.
Both input fields have a ref and the button points to the user login function.
<TextInput
ref = {component => this._pin = component}
placeholder="pin"
onChangeText = {(pin) => this.setState({pin})}
secureTextEntry = {true}
onSubmitEditing={this._userLogin}
/>
<TouchableOpacity
onPress={this._userLogin}
title = "Submit"
disabled={this.state.isLoggingIn||!this.state.phoneNo||!this.state.pin}>
<Text style={styles.loginText}>Sign In</Text>
</TouchableOpacity>
try something like this.
I also get problem acceding both status code & data from fetch call, so i made "processResponse" function
processResponse=(response) =>{
const statusCode = response.status;
const data = response.json();
return Promise.all([statusCode, data]).then(res => {
return ({
statusCode: res[0], // the status code
data: res[1] // the data of the GET/POST returned by fetch call
})
}
);
}
_userLogin = () => {
console.log("userLogin");
this.setState({isLoggingIn: true, message:''});
var params = {
phoneNo: this.state.phoneNo,
pin: this.state.pin
};
fetch("https://"+"<url>", {
method: "POST",
headers: {
'Accept': 'application/json',
'Content-Type': 'application/json'
},
body: JSON.stringify(params)
})
/*processResponse return both status and data , because when you make
.then((response) => response.json()) you return only data and status is removed
*/
.then(this.processResponse)
.then(res => {
console.log("response of fetch",res);
const { statusCode, data } = res;
if (statusCode > 200) {
this.props.onLoginPress()
}else{
this.setState({ message: data.message });
console.log("data message" , data.message);
}
this.setState({ isLoggingIn: false })
})
.catch(err=> {
console.error(err);
this.setState({ message: err.message});
this.setState({isLoggingIn: false})
});
});
}
AlainIb was very helpful and this helped contribute to what worked in the end. Using form data seemed to assist with the JSON Parse error. Hope this helps anyone else who is having any troubles.
state = {
message: ''
}
_processResponse = (response) =>{
const statusCode = response.status;
console.log("resp", response);
const data = response.json();
console.log("data", data);
return Promise.all([statusCode, data]).then(res => {
return ({
statusCode: res[0], // the status code
data: res[1] // the data of the GET/POST returned by fetch call
})
});
}
_userLogin = () => {
console.log("userLogin");
this.setState({isLoggingIn: true, message:''});
var params = {
phoneno: this.state.phoneno,
pin: this.state.pin
};
var formData = new FormData();
formData.append("phoneno", this.state.phoneno);
formData.append("pin", this.state.pin);
console.log(formData);
let data = {
method: 'POST',
headers: {
'Accept': 'application/json',
'Content-Type':'multipart/form-data'
},
body: formData
}
console.log(data);
fetch("https://"+"url", data)
.then(this._processResponse)
.then(res => {
console.log("response of fetch",res);
const { statusCode, data } = res;
if (statusCode == 200) {
console.log("in if statement");
if(data.login_success== 1){
console.log("name to be passed", data.name);
console.log("log in to profile");
this.props.navigation.navigate('ProfileRoute');
}else {
console.log("fail");
this.setState({message:"Password or Phone Number is Wrong"});
}
}else{
this.setState({ message: data.message });
console.log("data message" , data.message);
}
this.setState({ isLoggingIn: false })
})
.catch(err=> {
console.error(err);
this.setState({ message: err.message});
this.setState({isLoggingIn: false})
});
}
I'm using fetch for requests, and I want to submit a file along with other data. How can I do so?
If it is not possible using fetch, what should I do then?
Thanks you guys.
react-native-fs
Has support for file upload on iOS
From the README:
// require the module
var RNFS = require('react-native-fs');
var uploadUrl = 'http://requestb.in/XXXXXXX'; // For testing purposes, go to http://requestb.in/ and create your own link
// create an array of objects of the files you want to upload
var files = [
{
name: 'test1',
filename: 'test1.w4a',
filepath: RNFS.DocumentDirectoryPath + '/test1.w4a',
filetype: 'audio/x-m4a'
}, {
name: 'test2',
filename: 'test2.w4a',
filepath: RNFS.DocumentDirectoryPath + '/test2.w4a',
filetype: 'audio/x-m4a'
}
];
var uploadBegin = (response) => {
var jobId = response.jobId;
console.log('UPLOAD HAS BEGUN! JobId: ' + jobId);
};
var uploadProgress = (response) => {
var percentage = Math.floor((response.totalBytesSent/response.totalBytesExpectedToSend) * 100);
console.log('UPLOAD IS ' + percentage + '% DONE!');
};
// upload files
RNFS.uploadFiles({
toUrl: uploadUrl,
files: files,
method: 'POST',
headers: {
'Accept': 'application/json',
},
fields: {
'hello': 'world',
},
begin: uploadBegin,
progress: uploadProgress
})
.then((response) => {
if (response.statusCode == 200) {
console.log('FILES UPLOADED!'); // response.statusCode, response.headers, response.body
} else {
console.log('SERVER ERROR');
}
})
.catch((err) => {
if(err.description === "cancelled") {
// cancelled by user
}
console.log(err);
});