Hey Ive run into a little problem in my SQL/PHP/JAVA application Im hoping you guys can help :)
I have a java application that when run is connected to my website when the java application validates that it is running it talks to my website and my website assigns a session Id to both the java application and the website itself.
cool we good so far?
alright my java application sends data at regular intervals to a page called Dashboard.php what I would like to do is save the data into my Mysql table then when new data is received by Dashboard.php from my java application where the sessionID is the same I would like the table to update to the new data that was just received
here is the php i have so far although it doesnt work.
function update($script_name, $version, $runtime, $status, $ranged, $attack, $defense, $strength, $magic, $sessionID, $username)
{
global $db;
$sql = "SELECT * FROM Dashboard WHERE session_id = '$sessionID'";
try {
$results = $db->query($sql);
if ($results->rowCount() <= 0) {
$query = "INSERT INTO Dashboard (script_name, version, runtime, status, ranged, attack, defense, strength, magic, session_id, username) VALUES ('$script_name', '$version', '$runtime', '$status', '$ranged', '$attack', '$defense', '$strength', '$magic', '$sessionID', $username)";
$db->exec($query);
} else {
foreach ($results as $row) {
$timerunnew = $row['runtime'] + $runtime;
$v4new = $row['ranged'] + $range;
$v5new = $row['attack'] + $attack;
$v6new = $row['defense'] + $defense;
$v7new = $row['strength'] + $strength;
$v8new = $row['magic'] + $magic;
}
$db->exec("UPDATE Dashboard SET `runtime` = $timerunnew, `ranged` = $v4new, `attack` = $v5new, `defense` = $v6new, `strength` = $v7new, `magic` = $v8new WHERE session_id = '$sessionID'");
}
} catch (PDOException $ex) {
echo "fail";
}
}
Ive also tried experimenting with ON DUPLICATE KEY UPDATE value = VALUES(value) however I have had no luck does anyone have a solution? any help would be much appreciated
If this is the only way that records can be inserted into the Dashboard table, then it is impossible for two records to share the same session_id (save for a race hazard occurring between the SELECT and INSERT commands). In which case, you should:
Ensure that there is a UNIQUE key defined on session_id:
ALTER TABLE Dashboard ADD UNIQUE KEY (session_id);
Use INSERT ... ON DUPLICATE KEY UPDATE, ideally with a properly parameterised prepared statement:
$qry = $db->prepare('
INSERT INTO Dashboard (
script_name, version, runtime, status, ranged, attack,
defense, strength, magic, session_id, username
) VALUES (
:script_name, :version, :runtime, :status, :ranged, :attack,
:defense, :strength, :magic, :session_id, :username
) ON DUPLICATE KEY UPDATE
runtime = runtime + VALUES(runtime),
attack = attack + VALUES(status),
defense = defense + VALUES(defense),
strength = strength + VALUES(strength),
magic = magic + VALUES(magic)
');
$qry->execute([
':script_name' => $script_name,
':version' => $version,
':runtime' => $runtime,
':status' => $status,
':ranged' => $ranged,
':attack' => $attack,
':$defense' => $defense,
':strength' => $strength,
':magic' => $magic,
':session_id' => $sessionID,
':username' => $username
]);
Related
Here is my goal
1. I have only one ID send from the server with list of string separated comma
this how it look like: ID=1, names=blue,red,green,yellow
2. This is my attempt:
2.1 i try to change the names to arrays by using this code
$myString = "Red,Blue,Black";
$myArray = explode(',', $myString);
2.2 and i try my insertion like this:
$sql="INSERT INTO `cat_interest`(`id`,`categories`) VALUES (1,'".$myArray["categories"]."'";
if (!$result = $mysqli->query($sql)){
$message = array('Message' => 'insert fail');
echo json_encode($message);
}else{
$message = array('Message' => 'new record inserted');
echo json_encode($tempArray);
}
Here is my complete code view
<?php
define('HOST','serveraddress');
define('USER','root');
define('PASS','pass');
define('DB','dbname');
ini_set('display_errors',1);
//ini_set('display_startup_errors', 1);
error_reporting(E_ALL);
$mysqli = new mysqli(HOST,USER,PASS,DB);
$message= array();
$myString = "Red,Blue,Black";// incoming string comma names
$myArray = explode(',', $myString);
$sql="INSERT INTO `cat_interest`(`id`,`categories`) VALUES (1,'".$myArray["categories"]."'";
if (!$result = $mysqli->query($sql)){
$message= array('Message' => 'insertion failed');
echo json_encode($message);
}else{
$message= array('Message' => 'new record inserted');
echo json_encode($message);
} ?>
This is what i want to achieve below
TABLE
ID Categories
1 RED
1 Blue
1 Black
after insertion
Please help i don't know what i doing wrong
While that SQL is invalid, you never close the values. Explode also doesn't build an associated array.
A rough example of how you could build a valid SQL statement would be
$myString = "Red,Blue,Black";// incoming string comma names
$myArray = explode(',', $myString);
print_r($myArray);
$sql = "INSERT INTO `cat_interest`(`id`,`categories`) VALUES";
foreach($myArray as $value){
$sql .= " (1, '{$value}'),";
}
$sql = rtrim($sql, ',');
Demo: https://eval.in/587840
When in doubt about how an array in constructed use print_r or var_dump. When having an issue with a query in mysqli use error reporting, http://php.net/manual/en/mysqli.error.php.
Also in your current usage you aren't open to SQL injections but if $myString comes from user input, or your DB you could be. You should look into using parameterized queries; http://php.net/manual/en/mysqli.quickstart.prepared-statements.php.
I want to allow a user to authenticate and retrieve a full list of Active Directory users without having to enter their password. I'm able to authenticate easily through Waffle and can query information specific to the authenticated user, like the list of groups to which they belong. However, Waffle doesn't seem to have the ability to make more general queries like the full list of users (or even the list of users belonging to a certain group).
I have another toy example configured where I use the JNDI to query the user list, which works fine, but it requires a username and password in order to make the connection.
Assuming anonymous querying is disabled on my AD server, is there any way for me to use the authenticated session I've established through Waffle to query the list of users?
Figured it out, in case anyone is interested. Honestly surprised I didn't get an answer or find a clear-cut solution somewhere online. It turns out that Waffle is unnecessary for a simple user list query - I modified the code sample here to produce the following method which does the trick:
static void queryCom4j(){
IADs rootDSE = COM4J.getObject(IADs.class, "LDAP://RootDSE", null);
String namingContext = (String)rootDSE.get("defaultNamingContext");
_Connection conn = ClassFactory.createConnection();
conn.provider("ADsDSOObject");
conn.open("Active Directory Provider","","",-1);
_Command cmd = ClassFactory.createCommand();
cmd.activeConnection(conn);
String fields = "distinguishedName,userPrincipalName,telephoneNumber,mail";
String query = "(&(objectclass=user)(objectcategory=person))";
cmd.commandText("<LDAP://" + namingContext + ">;" + query + ";" + fields + ";subTree");
_Recordset rs = cmd.execute(null, Variant.getMissing(), -1);
System.out.println("Found " + rs.recordCount() + " users");
while (!rs.eof()){
for (int i = 0; i < fields.split(",").length; i++){
Object value = rs.fields().item(i).value();
System.out.println((value == null) ? "N/A" : value.toString());
}
rs.moveNext();
}
Trying to use a similar example from the sample code found here
My sample function is:
void query()
{
String nodeResult = "";
String rows = "";
String resultString;
String columnsString;
System.out.println("In query");
// START SNIPPET: execute
ExecutionEngine engine = new ExecutionEngine( graphDb );
ExecutionResult result;
try ( Transaction ignored = graphDb.beginTx() )
{
result = engine.execute( "start n=node(*) where n.Name =~ '.*79.*' return n, n.Name" );
// END SNIPPET: execute
// START SNIPPET: items
Iterator<Node> n_column = result.columnAs( "n" );
for ( Node node : IteratorUtil.asIterable( n_column ) )
{
// note: we're grabbing the name property from the node,
// not from the n.name in this case.
nodeResult = node + ": " + node.getProperty( "Name" );
System.out.println("In for loop");
System.out.println(nodeResult);
}
// END SNIPPET: items
// START SNIPPET: columns
List<String> columns = result.columns();
// END SNIPPET: columns
// the result is now empty, get a new one
result = engine.execute( "start n=node(*) where n.Name =~ '.*79.*' return n, n.Name" );
// START SNIPPET: rows
for ( Map<String, Object> row : result )
{
for ( Entry<String, Object> column : row.entrySet() )
{
rows += column.getKey() + ": " + column.getValue() + "; ";
System.out.println("nested");
}
rows += "\n";
}
// END SNIPPET: rows
resultString = engine.execute( "start n=node(*) where n.Name =~ '.*79.*' return n.Name" ).dumpToString();
columnsString = columns.toString();
System.out.println(rows);
System.out.println(resultString);
System.out.println(columnsString);
System.out.println("leaving");
}
}
When I run this in the web console I get many results (as there are multiple nodes that have an attribute of Name that contains the pattern 79. Yet running this code returns no results. The debug print statements 'in loop' and 'nested' never print either. Thus this must mean there are not results found in the Iterator, yet that doesn't make sense.
And yes, I already checked and made sure that the graphDb variable is the same as the path for the web console. I have other code earlier that uses the same variable to write to the database.
EDIT - More info
If I place the contents of query in the same function that creates my data, I get the correct results. If I run the query by itself it returns nothing. It's almost as the query works only in the instance where I add the data and not if I come back to the database cold in a separate instance.
EDIT2 -
Here is a snippet of code that shows the bigger context of how it is being called and sharing the same DBHandle
package ContextEngine;
import ContextEngine.NeoHandle;
import java.util.LinkedList;
/*
* Class to handle streaming data from any coded source
*/
public class Streamer {
private NeoHandle myHandle;
private String contextType;
Streamer()
{
}
public void openStream(String contextType)
{
myHandle = new NeoHandle();
myHandle.createDb();
}
public void streamInput(String dataLine)
{
Context context = new Context();
/*
* get database instance
* write to database
* check for errors
* report errors & success
*/
System.out.println(dataLine);
//apply rules to data (make ContextRules do this, send type and string of data)
ContextRules contextRules = new ContextRules();
context = contextRules.processContextRules("Calls", dataLine);
//write data (using linked list from contextRules)
NeoProcessor processor = new NeoProcessor(myHandle);
processor.processContextData(context);
}
public void runQuery()
{
NeoProcessor processor = new NeoProcessor(myHandle);
processor.query();
}
public void closeStream()
{
/*
* close database instance
*/
myHandle.shutDown();
}
}
Now, if I call streamInput AND query in in the same instance (parent calls) the query returns results. If I only call query and do not enter ANY data in that instance (yet web console shows data for same query) I get nothing. Why would I have to create the Nodes and enter them into the database at runtime just to return a valid query. Shouldn't I ALWAYS get the same results with such a query?
You mention that you are using the Neo4j Browser, which comes with Neo4j. However, the example you posted is for Neo4j Embedded, which is the in-process version of Neo4j. Are you sure you are talking to the same database when you try your query in the Browser?
In order to talk to Neo4j Server from Java, I'd recommend looking at the Neo4j JDBC driver, which has good support for connecting to the Neo4j server from Java.
http://www.neo4j.org/develop/tools/jdbc
You can set up a simple connection by adding the Neo4j JDBC jar to your classpath, available here: https://github.com/neo4j-contrib/neo4j-jdbc/releases Then just use Neo4j as any JDBC driver:
Connection conn = DriverManager.getConnection("jdbc:neo4j://localhost:7474/");
ResultSet rs = conn.executeQuery("start n=node({id}) return id(n) as id", map("id", id));
while(rs.next()) {
System.out.println(rs.getLong("id"));
}
Refer to the JDBC documentation for more advanced usage.
To answer your question on why the data is not durably stored, it may be one of many reasons. I would attempt to incrementally scale back the complexity of the code to try and locate the culprit. For instance, until you've found your problem, do these one at a time:
Instead of looping through the result, print it using System.out.println(result.dumpToString());
Instead of the regex query, try just MATCH (n) RETURN n, to return all data in the database
Make sure the data you are seeing in the browser is not "old" data inserted earlier on, but really is an insert from your latest run of the Java program. You can verify this by deleting the data via the browser before running the Java program using MATCH (n) OPTIONAL MATCH (n)-[r]->() DELETE n,r;
Make sure you are actually working against the same database directories. You can verify this by leaving the server running. If you can still start your java program, unless your Java program is using the Neo4j REST Bindings, you are not using the same directory. Two Neo4j databases cannot run against the same database directory simultaneously.
Spaces not changing to underscored when sent from Java-->PHP-->SQL
Java code:
String urlString = "http://www.mysite.com/auth/verifyuser.php?name="+name.toLowerCase().replace(" ","_");
PHP code:
$name = mysql_real_escape_string($_GET['name']);
$name = str_replace(' ', '_', $name);
$query = "select * from authinfo where name LIKE '$name'";
mysql_query($query);
$num = mysql_affected_rows();
if ($num > 0) {
echo '1';
} else {
echo '0';
}
when I implement a test log on the SQL database, it somehow still seems to show up with spaces instead of underscores(even though I replace it in Java and PHP) and the PHP file returns '0' rather than '1'. I've heard the issue might be whitespaces? It seems to happen to only certain users, mostly mac users.
If your php file is returning a 0, that means your query is not getting executed. Where are you establishing a connection with the database before executing the query?
Remark: where name = '$name'
mysql_affected_rows concerns INSERT, UPDATE and DELETE.
$r = mysql_query($query);
$num = mysql_num_rows($r);
It's unsafe to pass raw name into URL without encoding it.
String urlString = "http://www.example.com/auth/verifyuser.php?name=" + URLEncoder.encode(name.toLowerCase(), "UTF-8");
In PHP you can obtain data:
$name = urldecode($_GET['name']);
I have a List which shows Users
<g:form action="listUsers">
<g:select id="userListe" name="selectedUser" size="10" onchange="this.form.submit()"
from="${users.idToShow}"
value="${selectedUser.idToShow}"/>//edit: idToShow, not itToShow
</g:form>
I implemented a search function with JQuery, this one works so far
$(function() {
//When user types, start searching
$('#userSearch').keyup(function() {
$.post(search_url, { query: this.value },
//data stores the found values from server (works)
function(data) {
//first, remove all the values from the userList
$('#userListe').find('option').remove();
//split userID and Value, not important
var userArray = data.split(";");
for (var i = 0; i < userArray.length; i++) {
//split userID and Value, not important
var name = userArray[i].split(':')[0]
var id = userArray[i].split(':')[1]
/*
* This Line solves the problem. Now the Server knows it´s a User
*/
$j('#userListe').append('<option value="'+name+'">'+name+'</option>'
});
});
})
The search shows the correct User, but if I click on one (to change values for example), the server doesnt know it's a User, and just shows a null pointer exception.
I know this is kinda interdisciplinary stuff and maybe a bit to large for a support question, but Ill be happy about any small clue.
Thanks a lot, Daniel
method listUsers:
def listUsers = {
def foundUsers
def users
def selectedUser
foundUsers = User.list()
users = User.list(fetch: [User: foundUsers.IdToShow])
users.sort {it.IdToShow}
selectedUser = users.get(0)
if (params.selectedUser) {
selectedUser = User.findByIdToShow(params.selectedUser)
}
[users: users, selectedUser: selectedUser]