Php : get formData base64 image string and upload to local folder - php

I have base64 image string sending in my API calling to a .php file
Request URL :
http://localhost/server/index.php?saveImageToFolder=true?id=1&name=fdsfsdf
My HTML form looke like below
Below is my code for sending base64 from Input type file which is in reactjs
function getBase64(file) {
return new Promise(function (resolve, reject) {
const reader = new FileReader();
reader.onload = function () {
resolve(reader.result);
};
reader.onerror = reject;
reader.readAsDataURL(file);
});
}
const onChangeImage = (e, id, slotname) => {
const formData = new FormData();
formData.append('file', e.target.files[0]);
const fileFound = e.target.type === 'file' && e.target.files[0];
const promise = fileFound && getBase64(fileFound);
promise.then(function(result) {
uploadImage({ 'id': id, 'slotname': slotname, 'slotimage': result });
})
}
And then i have formData in my payload. Below is the complete network tab payload
My index.php
header("Access-Control-Allow-Origin: *");
header("Content-Type: application/json");
header("Access-Control-Allow-Methods: GET, POST, PUT, DELETE, OPTIONS");
header("Access-Control-Max-Age: 3600");
header("Access-Control-Allow-Headers: Content-Type, Access-Control-Allow-Headers, Authorization, X-Requested-With");
include("connect.php");
error_reporting(0);
session_start();
if(isset($_GET['saveImageToFolder'])){
var_dump($_POST['file']); //This is showing NULL
var_dump($_FILES['file']); //This is also showing NULL
$data = $_POST['file'];
list($type, $data) = explode(';', $data);
list(, $data) = explode(',', $data);
$data = base64_decode($data);
file_put_contents('image.png', $data);
}
Image file is creating with PNG and 0KB. Not getting how to fetch values of formData and then further in index.php

const fileFound = e.target.type === 'file' && e.target.files[0];
evaluates to true or false and in the next step you pass a boolean to getBase64() instead of the filename.
const promise = fileFound && getBase64(fileFound);
So change it to
const promise = fileFound && getBase64(file);
instead.

Related

PHP not getting data sent by post from React in Development, whereas Postman works

Given the following code:
fetch(mockproxy+myphp.php,{
method: 'POST',
headers:{'Token':token["token"]},
body: name,
}).then((response) => response.json())
.then((json)=>{
toast.success(JSON.stringify(json));
})
.catch((err) => {
toast.error(JSON.stringify(err));
})
}
mockproxy is helping bypass CORSS. The file looks like this:
const corsAnywhere = require('cors-anywhere');
const express = require('express');
const apicache = require('apicache');
const expressHttpProxy = require('express-http-proxy');
const CORS_PROXY_PORT = 5000;
// Create CORS Anywhere server
corsAnywhere.createServer({}).listen(CORS_PROXY_PORT, () => {
console.log(
`Internal CORS Anywhere server started at port ${CORS_PROXY_PORT}`
);
});
// Create express Cache server
let app = express();
// Register cache middleware for GET and OPTIONS verbs
app.get('/*', cacheMiddleware());
app.options('/*', cacheMiddleware());
// Proxy to CORS server when request misses cache
app.use(expressHttpProxy(`localhost:${CORS_PROXY_PORT}`));
const APP_PORT = process.env.PORT || 5080;
app.listen(APP_PORT, () => {
console.log(`External CORS cache server started at port ${APP_PORT}`);
});
/**
* Construct the caching middleware
*/
function cacheMiddleware() {
const cacheOptions = {
statusCodes: { include: [200] },
defaultDuration: 60000,
appendKey: (req, res) => req.method
};
let cacheMiddleware = apicache.options(cacheOptions).middleware();
return cacheMiddleware;
}
And the server is a shared server where I upload the PHP files so they can access to the DB. The php receives the data and give a response when I use postman but not when I execute the fetch from the dev website, I'm using react, I think it doesn't matter in this case.
The PHP file:
<?php
$headers = apache_request_headers();
header("Access-Control-Allow-Origin: *, ");
header("Access-Control-Allow-Methods: HEAD, GET, POST, PUT, PATCH, DELETE, OPTIONS");
header("Access-Control-Allow-Headers: X-API-KEY, Origin, X-Requested-With, Content-Type, Accept, Access-Control-Request-Method,Access-Control-Request-Headers, Authorization");
header('Content-Type: application/json');
$method = $_SERVER['REQUEST_METHOD'];
if ($method == "OPTIONS") {
header('Access-Control-Allow-Origin: *');
header("Access-Control-Allow-Headers: X-API-KEY, Origin, X-Requested-With, Content-Type, Accept, Access-Control-Request-Method,Access-Control-Request-Headers, Authorization");
header("HTTP/1.1 200 OK");
exit;
}
if (isset($_POST["name"])) {
echo json_encode(" name" . $_POST["name"]); //returned on postman
}else{
echo json_encode("no name"); //returned on development.
}
exit;
So this is a code i use when i want to fetch all data from a form. You can obviously not loop through all forms like i do below but just your single form.
// Query all forms in the DOM or a specific one if you want
const forms = document.querySelectorAll('form');
// Loop through them
forms.forEach((form) => {
// if method is post
if (form.method === 'post') {
form.addEventListener('submit', (event) => {
// prevent default submit
event.preventDefault();
// prepare the data
let data = new FormData(form);
// fetch using the form's
fetch(form.action, {
method: 'post',
body: data,
})
// get the text() from the Response object
.then(response => response.text())
.then(text => {
// Display it in the result div
document.getElementById('result').innerHTML = text;
})
}, false);
// if not post (get really)
} else {
form.addEventListener('submit', (event) => {
// prevent default submit
event.preventDefault();
// build the URL query params from the submitted data
const data = new URLSearchParams(new FormData(form).entries());
// Fetch, URL is formed from the action, append ? and then the query params
fetch(form.action + '?' + data)
// get the text() from the Response object
.then(response => response.text())
.then(text => {
// Display it in the result div
document.getElementById('result').innerHTML = text;
})
}, false);
}
});

Retrieving a parameter value from an httpClient response in angular6 with a php API?

I have a method in angular that posts values to a php api, when http post is successful, I get a json response, but when I try to access res.status or any parameter in the json object I get Property 'status' does not exist on type 'Object'. How can I get the value of a parameter in the response object?
Here is my angular class
export class QuizComponent implements OnInit {
constructor(private http: HttpClient) { }
myData = { param1: 'This is param 1', param2: 'this is param 2' }
sendmydata(){
const req = this.http.post('http://myhost.com/phpapi/api.php',this.myData)
.subscribe(
res => {
console.log(res);
// how can I access res.status here?
res.status;//this line says Property 'status' does not exist on type 'Object'
},
err => {
console.log("Error occured");
}
);
}
and here is my PHP :
(I know about prepared statements, just keeping it simple here):
<?php
header("Access-Control-Allow-Origin: *");
header("Content-Type: application/json; charset=UTF-8");
header("Access-Control-Allow-Methods: POST");
header("Access-Control-Max-Age: 3600");
header("Access-Control-Allow-Headers: Content-Type, Access-Control-
Allow-Headers, Authorization, X-Requested-With");
$db = "dbname";//Your database name
$dbu = "dbuser";//Your database username
$dbp = "dbpass";//Your database users' password
$host = "localhost";//MySQL server - usually localhost
$dblink = mysql_connect($host,$dbu,$dbp);
$seldb = mysql_select_db($db);
$postdata = file_get_contents("php://input");
$request = json_decode($postdata);
$item1 = $request->param1;
$item2 = $request->param;
$sql = mysql_query("INSERT INTO `$db`.`table` (`id`,`item1`,`item2`)
VALUES ('','$item1','$item2');");
if($sql){
if (strcmp($item1, "") != 0) {
echo '{"status":"ok"}';
}
}else{
echo '{"status":"error"}';
}
mysql_close($dblink);//Close off the MySQL connection to save resources.
?>
Assuming you have an interface defined for your response:
interface Response {
status: string;
}
Add the type information to your post call:
this.http.post<Response>('http://myhost.com/phpapi/api.php',this.myData)
or any, if no type definition available
this.http.post<any>('http://myhost.com/phpapi/api.php',this.myData)

Ionic 3 - Upload Image, PDF and form data in single HTTP request

I am working on an Ionic 3 app. Where I need to upload the Image file, PDF file and form data in a single HTTP request.
I have tried Cordova file transfer plugin also but for that I have to call multiple requests (one for image and one for PDF), which I don't want to do.
I have tried each and every solution from google, but I couldn't find the right solution because each and every solution is for upload the image.
I am using PHP as backend. Please let me know where I am making the mistake.
This is HTML
<form (ngSubmit)="submitLicence()" [formGroup]="licence" enctype="multipart/form-data">
<ion-list inset>
<ion-item>
<ion-label>Licence Type</ion-label>
<ion-input type="text" formControlName="licence_type" placeholder="Value"></ion-input>
</ion-item>
<ion-item>
<ion-label>State</ion-label>
<ion-input type="text" formControlName="state" placeholder="Value"></ion-input>
</ion-item>
<ion-item>
<ion-label>Year</ion-label>
<ion-input type="number" formControlName="year" placeholder="Value"></ion-input>
</ion-item>
<ion-item>
<ion-label>Select PDF</ion-label>
<ion-icon name="md-add-circle" item-end color="secondary" (click)="selectPDF()"></ion-icon>
</ion-item>
<ion-item>
<ion-label>Take a Photo</ion-label>
<ion-icon name="md-add-circle" item-end color="secondary" (click)="presentActionSheet()"></ion-icon>
</ion-item>
</ion-list>
<div padding>
<button ion-button type="submit" type="submit" [disabled]="!licence.valid" block>Submit</button>
</div>
</form>
These functions are for upload pdf.
selectPDF(){
this.fileChooser.open()
.then(uri =>
{(<any>window).FilePath.resolveNativePath(uri, (result) => {
let loaderPdf = this.loadingCtrl.create({
content: "Uploading PDF..."
});
loaderPdf.present();
// this.fd.append('doc',result);
this.testResponse = result;
this.nativepath = result;
this.readfile(loaderPdf);
})
})
.catch(e =>
this.testResponse = 'Error - '+e);
}
readfile(loaderPdf) {
(<any>window).resolveLocalFileSystemURL(this.nativepath, (res) => {
res.file((resFile) => {
var reader = new FileReader();
// reader.readAsArrayBuffer(resFile);
reader.onloadend = (evt: any) => {
loaderPdf.dismiss();
var src = evt.target.result;
src = src.split("base64,");
var contentAsBase64EncodedString = src[1];
var contentType = src[0].split(':');
this.testResponse = contentType[1].replace(';','');
contentType = JSON.stringify(contentType[1].replace(';',''));
var fileBlob = new Blob([evt.target.result], { type: contentType});
this.fd.append('doc',fileBlob,'doc');
//do what you want to do with the file
}
reader.readAsDataURL(resFile);
})
})
}
These functions are to select images.
public presentActionSheet() {
let actionSheet = this.actionSheetCtrl.create({
title: 'Select Image Source',
buttons: [
{
text: 'Load from Library',
handler: () => {
this.takePicture(this.camera.PictureSourceType.PHOTOLIBRARY);
}
},
{
text: 'Use Camera',
handler: () => {
this.takePicture(this.camera.PictureSourceType.CAMERA);
}
},
{
text: 'Cancel',
role: 'cancel'
}
]
});
actionSheet.present();
}
public takePicture(sourceType) {
let loaderImage = this.loadingCtrl.create({
content: "Uploading Image..."
});
loaderImage.present();
var options = {
quality: 100,
sourceType: sourceType,
saveToPhotoAlbum: false,
correctOrientation: true
};
// Get the data of an image
this.camera.getPicture(options).then((imageData) => {
// Special handling for Android library
this.base64Image = imageData;
this.readImage(loaderImage);
}, (err) => {
this.presentToast('Error while selecting image.');
});
}
readImage(loaderImage) {
(<any>window).resolveLocalFileSystemURL(this.base64Image, (res) => {
res.file((resFile) => {
var reader = new FileReader();
// reader.readAsArrayBuffer(resFile);
reader.onloadend = (evt: any) => {
var src = evt.target.result;
src = src.split("base64,");
var contentAsBase64EncodedString = src[1];
var contentType = src[0].split(':');
this.testResponse = contentType[1].replace(';','');
contentType = JSON.stringify(contentType[1].replace(';',''));
var imageBlob = new Blob([evt.target.result], { type: contentType});
loaderImage.dismiss();
this.fd.append('image',imageBlob,'image');
//do what you want to do with the file
}
reader.readAsDataURL(resFile);
})
})
}
And finally, this function is for post the form.
submitLicence(){
const licenceFormValue = JSON.stringify(this.licence.value);
let loader = this.loadingCtrl.create({
content: "Submitting form..."
});
loader.present();
var lt = this.licence.value.licence_type;
var st = this.licence.value.state;
var yr = this.licence.value.year;
this.fd.append('type',lt);
this.fd.append('state',st);
this.fd.append('year',yr);
this.fd.append('mode','createNewLicence');
this.testResponse = licenceFormValue;
let headers = new HttpHeaders();
headers = headers.set('Content-Type', 'application/json; charset=utf-8');
this.lic = this.httpClient.post('http://website.com/api.php',this.fd,{headers:headers});
this.lic.subscribe(data => {
loader.dismiss();
this.testResponse = JSON.stringify(data);
})
}
This is PHP script to upload data and images as well.
error_reporting(0);
date_default_timezone_set('GMT');
require_once './config/config_live.php';
include_once PATH_FRONT_LIBRARY . 'adodb5/adodb.inc.php';
include_once PATH_FRONT_LIBRARY . "ADODBClass_mysql.php";
include_once PATH_FRONT_LIBRARY_MAILER . "phpmailer/class.phpmailer.php";
include_once PATH_FRONT_LIBRARY_MAILER . "sendEmail.php";
header('Access-Control-Allow-Origin: *');
header("Access-Control-Allow-Credentials: true");
header('Access-Control-Allow-Methods: GET, PUT, POST, DELETE, OPTIONS');
header('Access-Control-Max-Age: 1000');
header('Access-Control-Allow-Headers: Content-Type, Content-Range, Content-
Disposition, Content-Description');
if ($_POST['json']) {
$data = json_decode($_POST['json'], true);
} else {
$jsonString = file_get_contents('php://input');
$jsonObj = json_decode($jsonString, true);
$data = $jsonObj;
}
if ($data["key"] == "difsfk") {
NOTE: The PHP API on which I am working is created by another person and I have to write ionic code as per PHP code.
have you tried with ionic native http library
please follow link : https://ionicframework.com/docs/native/http/
in body send your image and file data and other param.
post(url, body, headers)
For example :
let body = new FormData();
body.append(‘image’, imagedata);
body.append(‘pdf’, pdfdata);
body.append(‘desc’, “testing”);
this.http.post(“Your api endpoint”, body, options).subscribe(res => {
console.log(res);
});

Can't figure out how to upload a serializedObject and a file via AJAX

I have a regular multipart/form-data that has some fields and 1 fileinput. I then send it to my php via:
$(document).on('submit', '#create-event-form', function(){
var form_data = JSON.stringify($(this).serializeObject());
$.ajax({
url: "../api/event/create.php",
type : "POST",
contentType : 'application/json',
data : form_data,
success : function(result) {
showEvents();
},
error: function(xhr, resp, text) {
// show error to console
console.log(xhr, resp, text);
}
});
return false;
});
This is, in turn received and saved to my db using:
header("Access-Control-Allow-Origin: *");
header("Content-Type: application/json; charset=UTF-8");
header("Access-Control-Allow-Methods: POST");
header("Access-Control-Max-Age: 3600");
header("Access-Control-Allow-Headers: Content-Type, Access-Control-Allow-Headers, Authorization, X-Requested-With");
// get database connection
include_once '../config/database.php';
// instantiate event object
include_once '../objects/event.php';
$database = new Database();
$db = $database->getConnection();
$event = new Event($db);
// get posted data
$data = json_decode(file_get_contents("php://input"));
$now = new DateTime();
$timestamp = $now->getTimestamp();
$file = $_FILES['painting']['name'];
$extension = end(explode(".", $file));
$location = "painting/$timestamp" . $file . $extension;
//move_uploaded_file($_FILES['painting']['tmp_name'], $location);
// set event property values
$event->name = $data->name;
$event->max = $data->max;
$event->painting = $location;
// create the event
if($event->create()){
$arr = array('message' => 'Evt created.');
echo json_encode($arr);
}else{
$arr = array('message' => 'Error creating the event.');
echo json_encode($arr);
}
Now, if I only pass the form_data I can successfully save everything, however, the file never reaches the PHP because I can't use php://input with multipart/form-data. I'm aware of that, so I'm looking for some way around it.
I've tried to send the file as part of the data:{key:value} pair on the js side but I can't get that to work. I've been at this for several hours now but I can't fathom how to do it (hence why move_uploaded_fileis commented, right now there's nothing in $_FILES so it fails).
Can anyone suggest a way for me to do this, please?
HTML5 introduces FormData class that can be used to file upload with ajax.
https://developer.mozilla.org/en-US/docs/Web/API/FormData/FormData
I think you would be nice to pay attention to different plug-ins. Like:
https://fineuploader.com/demos.html
http://blueimp.github.io/jQuery-File-Upload/
And to combine your logic with the work of something like that
Also I think this answer can help you how to do file upload using jquery serialization .

AngularJS: Uploading file via angular JS

My current scenario is: I've doing nesting repetition like follow:
$scope.uploadPic = function(file)
{
alert($scope.taskdetails.id); //task_id e.g 21
alert($rootScope.job_id); //job_id e.g 12
file.upload = Upload.upload(
{
url: 'http://localhost/mobile-data/upload_file.php',
data: {
file: file,
task_id: $scope.taskdetails.id,
job_id: $rootScope.job_id
},
});
file.upload.then(function (response) {
$timeout(function () {
file.result = response.data;
});
}, function (response) {
if (response.status > 0)
$scope.errorMsg = response.status + ': ' + response.data;
}, function (evt) {
// Math.min is to fix IE which reports 200% sometimes
file.progress = Math.min(100, parseInt(100.0 * evt.loaded / evt.total));
});
}
but on my upload_file.php i can't receive the values for:
task_id: $scope.taskdetails.id,
job_id: $rootScope.job_id
in console.log they are working fine. but on server side it is not receiving. here is code of my upload_file.php
header('Access-Control-Allow-Origin: *');
header('Access-Control-Allow-Methods: GET, PUT, POST, DELETE, OPTIONS');
header('content-type: application/json; charset=utf-8');
$_POST = json_decode(file_get_contents('php://input'), true);
$task_id = $_POST["task_id"];
$file = $_FILES["file"];
$job_id = $_POST["job_id"];
var_dump($task_id);
var_dump($job_id);
but on var_dump it only print null. Help me to receive the values correctly..
In your php file remove the decode line that is:
$_POST = json_decode(file_get_contents('php://input'), true);
You dont need to decode because you are not receiving data into JSON encoded array...

Categories