I have a GWT app with inputs (let's say Name, Address, Email). After user input all the required fields and press submit button, a PHP page will display the inputs from the GWT app. How can I connect my GWT app to php? I'm using Request Builder now. Do I still have to use XML to pass the GWT inputs to PHP? Please help. I'm just starting to learn GWT here.
Thanks in advance.
You actually don't need RequestBuilder for something like that.
It would be sufficient if you redirect to the PHP url and append your inputs as GET parameters.
So for example in the click handler you can do something like that:
submitButton.addClickHandler(new ClickHandler() {
public void onClick(ClickEvent event) {
String linkURL = "somePage.php?name="+name+"&address="+address+"&email="+email;
Window.Location.assign(linkURL);
}
});
and then in the PHP page you can retrieve the parameters in this way:
$name = $_GET['name'];
$address = $_GET['address'];
$email = $_GET['email'];
Update
If you want to use RequetBuilder you have to do something like that:
submitButton.addClickHandler(new ClickHandler() {
public void onClick(ClickEvent event) {
RequestBuilder request = new RequestBuilder(POST,PHP_URL);
JSONObject jsonValue = new JSONObject();
jsonValue.put("name", new JSONString(name));
jsonValue.put("address", new JSONString(address));
jsonValue.put("email", new JSONString(email));
request.setHeader("Content-Type", "application/json");
request.sendRequest(jsonValue.toString(),new RequestCallback() {
#Override
public void onResponseReceived(Request request, Response response) {
if (200 == response.getStatusCode()) {
//retrieve a uniqueid or so and redirect to the PHP page which displays the infos
} else {
// displayError("Couldn't retrieve
}
}
#Override
public void onError(Request request, Throwable exception) {
//displayError("Couldn't retrieve JSON");
}
});
}
});
On the server you just access the global $_POST variable to get the values:
$name = #_POST['name']
Related
I'm facing a frustrating problem right now and I can't see any reason why this doesn't work since is pure Unity developer copy paste code.
I can't send data from Unity to website. Every Unity sent parameter is taken as empty.
That's how my [Web.cs] looks like:
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using UnityEngine;
using UnityEngine.Networking;
public class Web : MonoBehaviour
{
public IEnumerator Login(string Username, string Password)
{
Debug.Log(Username);
Debug.Log(Password);
WWWForm Form = new WWWForm();
Form.AddField("loginUser", Username);
Form.AddField("loginPass", Password);
UnityWebRequest www = UnityWebRequest.Post("http://localhost/Login.php", Form);
yield return www.SendWebRequest();
if (www.isNetworkError || www.isHttpError)
Debug.Log(www.error);
else
{
Debug.Log("Form upload complete!");
Debug.Log(www.downloadHandler.text);
}
}
}
And I'm calling it via Login.cs
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
public class Login : MonoBehaviour
{
public InputField UserName;
public InputField Password;
public Button myButton;
private void Start()
{
myButton.onClick.AddListener(() =>
{
StartCoroutine(Main.Instance.Web.Login(UserName.text, Password.text));
});
}
}
The php code looks like:
<?php
$UserName = $_GET["loginUser"];
$Password = $_GET["loginPass"];
$myfile = fopen("testfile.txt", "a");
fwrite($myfile, "Username: $UserName\nPassowrd: $Password\n\n");
?>
So, when I manually acces the path link, I get the expected results:
http://localhost/Login.php?loginUser=Test&loginPass=Ok
https://i.imgur.com/s0bP5tJ.png
But when I do it with Unity, XAMPP writes the parameters as empty.
A debug photo:
https://i.imgur.com/r1IUTy2.png
It appears you're sending a POST request to a GET request.
Try this: UnityWebRequest.Get(...)
#Kale, thank you, I kinda still don't understand what's the difference between post and get methods :-?
For future searchers, that's how I managed to resolve the issue:
public class Web : MonoBehaviour
{
public IEnumerator Login(string Username, string Password)
{
WWWForm Form = new WWWForm();
string Link = "http://localhost/Login.php?loginUser=" + Username + "&loginPass=" + Password;
UnityWebRequest www = UnityWebRequest.Get(Link);
yield return www.SendWebRequest();
if (www.isNetworkError || www.isHttpError)
Debug.Log(www.error);
else
{
Debug.Log("Form upload complete!");
Debug.Log(www.downloadHandler.text);
}
}
}
In my website I’m using Stripe but for some reasons decided to change to Heartland Payment methods.
As I’m using laravel, so my knowledge is about controllers and models, I tried to understand how to do this with heartland but didn’t get it. For showing the input field it is working fine with me so now I want to make the payment by click submit button but I don’t know how to send these input information to controller to complete the payment.
Please I need good example showing process in the controller.
I tried to get the controller content from this link but didn't find clear one: https://developer.heartlandpaymentsystems.com/Ecommerce/Card
Thank you in advance
Here the code:
route:
Route::get('/Payment/Charge', 'PaymentController#heartlandPost')->name('heartlandpost');
Payment form and jquery code:
<form id="payment-form" action="/Payment/Charge" method="get">
<div id="credit-card"></div>
</form>
<script src="https://api2.heartlandportico.com/SecureSubmit.v1/token/gp-1.0.1/globalpayments.js"> </script>
<script type="text/javascript">
GlobalPayments.configure({
publicApiKey: "pkapi_cert_*****"
});
// Create Form
const cardForm = GlobalPayments.creditCard.form("#credit-card");
cardForm.on("token-success", (resp) => {
// add payment token to form as a hidden input
const token = document.createElement("input");
token.type = "hidden";
token.name = "payment_token";
token.value = resp.paymentReference;
// Submit data to the integration's backend for processing
const form = document.getElementById("payment-form");
form.appendChild(token);
form.submit();
});
cardForm.on("token-error", (resp) => {
// show error to the consumer
});
</script>
Controller:
public function heartlandPost()
{
}
So from reading the documentation, it looks like you need to do:
<?php
use GlobalPayments\Api\ServicesConfig;
use GlobalPayments\Api\ServicesContainer;
use GlobalPayments\Api\Entities\Address;
use GlobalPayments\Api\PaymentMethods\CreditCardData;
use GlobalPayments\Api\Entities\Exceptions\ApiException;
public function heartlandPost()
{
$config = new ServicesConfig();
$config->secretApiKey = "skapi_cert_***";
$config->developerId = "000000";
$config->versionNumber = "0000";
$config->serviceUrl = "https://cert.api2.heartlandportico.com";
ServicesContainer::configure($config);
$card = new CreditCardData();
$card->token = $request->input('payment_token');
$address = new Address();
$address->postalCode = $request->input('postal_code');
try {
$response = $card->charge(10)
->withCurrency("USD")
->withAddress($address)
->execute();
} catch (ApiException $e) {
// handle error
}
// return your response to the client
}
where you need to update the config to match your own keys and whatnot, and I''m not sure how you are passing the amount / postal code to your backend so make sure you do that as well.
I have a web server which contains a sql database. There are two "users" to this server/database. One is the actual user where they will submit changes through a UnityWebRequest using HTTP:Post. This will make changes to the database.
I have another system that is also in Unity, that needs to be notified, or somehow monitor for whenever a change is made to a specific table in a database. I don't know how to monitor the table for changes without constantly making select calls to the database.
What I've tried
I have a unity function which calls the webserver through HTTP:Post. The webserver goes into an infinite while loop making calls to the database something like
$variable = $_REQUEST['variable_to_monitor'];
$stmt = $pdo->prepare("SELECT variable_to_monitor FROM table_name;")
while(true){
$stmt->execute();
results = $stmt->fetchAll()[0];
if ($variable != results['variable_to_monitor']){
die(results['variable_to_monitor']);
}
}
This holds up the webserver and is making too many calls to the database.
I would like for Unity to be able to make a single call to a web server giving it a given state, the web server will compare said state to database until the database changes, then once the db changes respond to unity with the updated state. I want to be able to do this without making a million SELECT calls to a database per second.
Unity Code
void Update()
{
if(hasResponse)
{
hasResponse = false;
StartCoroutine(SendRequest());
}
}
IEnumerator SendRequest(WWWForm form = null, Action<string> callback = null)
{
if(null == form) form = new WWWForm();
form.AddField("request", "monitor_variable");
form.AddField("variable_to_monitor", this.variable_to_monitor);
UnityWebRequest www = UnityWebRequest.Post(url, form);
yield return www.SendWebRequest();
if (www.isNetworkError)
{
Debug.Log("Network Error");
}
else if (www.isHttpError)
{
Debug.Log("Http Error");
}
else
{
if(null == callback)
{
Debug.Log(www.downloadHandler.text);
}
else
{
if (!www.downloadHandler.text.Contains("New Request Started"))
{
hasResponse = true;
callback(www.downloadHandler.text);
}
else
{
Debug.Log(www.downloadHandler.text);
}
}
}
}
Of course you can and always should wait in Unity for the UnityWebRequest to finish! You should allways use e.g. a Coroutine
And than you can as well e.g. add a time offset so you don't make a new request right ahead but maybe wait a few seconds.
I personally would also add callbacks for the response which makes it way more flexible and reusable e.g.
public void MakeRepeatedRequests(string url, float timeOffset, Action<string> successCallback, Action<string> errorCallback)
{
StartCoroutine(RepeatedRequestRoutine(url, timeOffset, successCallback, errorCallback);
}
private IEnumerator RepeatedRequestRoutine(string url, float timeOffset, Action<string> successCallback, Action<string> errorCallback)
{
// No worries this still looks like a while loop (well it is ^^)
// but the yield makes sure it doesn't block Unity's UI thread
while(true)
{
// Configure your request
var request = UnityWebRequest.Post(url);
// Make the request and wait until the it has finished (has a response or timeout)
// a yield kind of tells this routine to leave, let Unity render this frame
// and continue from here in the next frame
yield return request.SendWebRequest();
if(request.isNetworkError || request.isHttpError)
{
errorCallback?.Invoke(request.error);
}
else
{
successCallback?.Invoke(request.downloadHandler.text);
}
// Now wait for the timeOffset
yield return new WaitForSeconds(timeOffset);
}
}
Now you can call it e.g. for waiting 2 seconds after the last request finished
// ...
MakeRepeatedRequests ("http://example.com", 2.0f, OnSuccess, OnError);
// ...
private void OnSuccess(string success)
{
Debug.LogFormat(this, "Nice it worked! Server said:/"{0}/"", success);
// Do something e.g. using success
}
private void OnError(string error)
{
Debug.LogFormat(this, "Oh no, request failed with \"{0}\"", error);
}
or also do the same thing using lambda expressions
MakeRepeatedRequests ("http://example.com", 2.0f,
success =>
{
Debug.LogFormat(this, "Nice it worked! Server said:/"{0}/"", success);
// Do something e.g. using success
},
error =>
{
Debug.LogFormat(this, "Oh no, request failed with \"{0}\"", error);
// Do something else
});
Even if you don't want the timeOffset this at least waits for every request to finish before starting the next one so your server only has to make one DB query and either return a success or an error.
In your case I would respond with a success (200) anyway (because error should be sent only if the server really had an error) but either send an empty string or some predefined one you can check for in Unity (something like e.g. "!NO_CHANGE!").
so on the server side without a loop something like e.g.
results = "SELECT * FROM table_name;"
if ($_REQUEST['variable_name'] != results['variable_name']){
echo results['variable_name'];
} else {
echo "!NO_CHANGE!";
}
than you could later in Unity check it
if(string.Equals(success, "!NO_CHANGE!")) return;
I'm new in PHP MVC, I have a question about how javascript works with php mvc
If I have a page with a button, when user click the button
It will send to next page and update data in database
$(document).ready(function(){
$("#btn").click(function(){
$.load(){... }
or $.post(){.....}//post data to another page
});
});
//next page
if(isset($_POST[])){
//update data
}
My question is
Should I send this data to controller than pass to model and output in view(if we need respond something)
Button --javascript--> controller -> model(update data) --send data back--> view
or
I can just send data to page and update without mvc
Sorry, i can't just comment your question yet
Your first approach is correct. Is recommended that you update data in models. Meanwhile, all SQL statements or ORM handles should be on it.
In your case, you have two options to show the data in view: Return a JSON in your php handle it with javascript, and load your view directly after update data. It depends how all your project is builded.
I can write some exemples, but you will need to give some peace of code.
// In your controller
if(isset($_POST)){
$obj = new MyObject();
$obj->name = $_POST['name'];
$obj->date = date("Y-m-d");
$obj->validatePost();
$obj->update();
$result = $obj->getData();
return $result;
}
// Your model
class MyObject {
public $name;
public $date;
public function validatePost(){
if($this->name == null){
// print error
}
}
public function update(){
// database cheets
}
public function getData(){
return $json;
}
}
I'm having a weird problem with android's webview. I load a page to the webview which has a link in it. I have set the webview to open that link in the same webview (not on a browser). When the next page is opened it writes some stuff to mysql. If an user has already opened that second page on a same day, the user gets redirected to the first page and no stuff is written to mysql. I noticed that in 1 out of 3-4 times on first situation pressing the link writes the stuff to mysql twice (with a same timestamp) and redirects the user right away to first page. So it seems that when the link is clicked the url is opened twice in a row. Everything works as supposed on my computer's browsers (safari, firefox and chrome). I found some article that said that empty src-fields on images can cause this but there are no empty src-fields in my php/html code.
Webview is set like this:
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_description);
WebViewClient yourWebClient = new WebViewClient()
{
public void onReceivedError(WebView view, int errorCode, String description, String failingUrl) {
webView.loadUrl("file:///android_asset/404.html");
}
#Override
public boolean shouldOverrideUrlLoading(WebView view, String url)
{
if ( url.contains("google") == false ) {
webView.loadUrl(url);
return false;
}
else {
Intent i = new Intent(Intent.ACTION_VIEW, Uri.parse(url));
startActivity(i);
return true;
}
}
};
webView = (WebView) findViewById(R.id.description);
webView.getSettings().setJavaScriptEnabled(true);
if (Build.VERSION.SDK_INT >= 11){
webView.setLayerType(View.LAYER_TYPE_SOFTWARE, null);
}
String url = (MainActivity.URL+"app/description.php?tagid="+tagId+"&screenwidth="+viewPortWidth+"&screenheight="+viewPortHeight+"&deviceid="+MainActivity.myDeviceId+"&lang="+MainActivity.myLanguage+"&os=android);
webView.setWebViewClient(yourWebClient);
webView.loadUrl(url);
}
My link is just a typical div inside an anchor tag (written in php):
echo '<a href="description.php?type='.$type.'&screenwidth='.$screenWidth.'&screenheight='.$screenHeight.'&tagid='.$tagid.'&no=1&deviceid='.$deviceid.'&lang='.$language.'">
<div class="redbutton">'.$lang['NO'].'</div></a>';
Actually only return false, webpage will automatically be loaded in WebView. No need to use webView.loadUrl();.
if ( url.contains("google") == false ) {
return false;
}
Give it a try and let me know if doesn't work.
As Documentation states -
while return false means the current WebView handles the url
Ok I found the reason for this. This was the cause:
#Override
public boolean shouldOverrideUrlLoading(WebView view, String url)
{
if ( url.contains("google") == false ) {
webView.loadUrl(url);
return false; // <----THIS LINE
}
else {
Intent i = new Intent(Intent.ACTION_VIEW, Uri.parse(url));
startActivity(i);
return false;
}
}
That should have returned true. I found this out by testing with this:
#Override
public void onPageFinished(WebView view, String url)
{
super.onPageFinished(view, url);
String url_new = view.getUrl();
Log.v("","Webview url: "+url_new);
}
I noticed that it printed out the url twice every time that some link was pressed, but it didn't do that when the webview was loaded first time. When I changed the return statement to true it only printed out once per click as it's supposed to do.