Just nu i M3-nätverket
Jump to content

Skapa en highscorelista kopplad till en java apple


domert

Recommended Posts

Hej!

 

Har skrivit ett spel i form av en javaapplet (http://www.anst.uu.se/dapdo451/). Nu vill jag ha en highscorelista som sparar värden om en spelare fått ett tillräckligt bra resultat. Eftersom appleten inte kan skriva till filer och eftersom jag inte kan använda cgi på servern (som inte är min egen) fick jag ett tips om php. Hur skulle ett sådant upplägg fungera? Kan php-skriptet öppna en textfil med sparade highscores, ta emot info från appleten om poängen, skriva till textfilen för att ändra den och visa highscorelistan på webbsidan? Om så är fallet, vore det kanon och jag skulle mer än gärna vilja veta hur ett sådant upplägg skulle se ut!

 

Tack på förhand!

 

/Daniel

 

Link to comment
Share on other sites

Du kan ju med appleten begära en sida från Internet, där du skickar med variabler. Problemet är då bara att göra det säkert.

 

Exempelvis öppnar du följande länk för att spara ett nytt resultat:

http://min.server.se/resultat.php?namn=Spelare&res=5642

 

Dock öppnar ju detta för att vem som helst kan infoga nya resultat i din databas.

 

Bättre är då att ditt applet först hämtar en hash-summa och ett id eller liknande från servern, som den använder för kryptering av resultatet.

Hash-summan sparas även på servern, som då kan kryptera upp resultatet, och istället ser då URLen du öppnar exempelvis ut så här:

http://min.server.se/resultat.php?res=Gdfd54jkbvsFfbju4F32rf&id=12364534

 

Du har IDt sparat i databasen, och kan därifrån hämta ut hash-summan som används som krypteringsnyckel.

 

Allt detta är enkelt att fixa med PHP, och borde inte vara några större problem att även implementera i appleten.

 

Säg till om du vill ha mer hjälp angående PHP-skriptet.

 

Kolla följande funktioner i PHP-manualen:

http://php.net/md5

http://php.net/crypt

 

Detta PEAR-paket är väldigt bra:

http://pear.php.net/package/Crypt_CBC

 

Link to comment
Share on other sites

Tack för svaret. Det låter som om min ide inte är omöjlig att genomföra i alla fall. Jag behöver lite mer detaljer och en del förtydliganden dock.

 

Spelet ligger på en sida (http://www.anst.uu.se/dapdo451/) på en server över vilken jag inte har någon kontroll och på vilken skript inte är tillåtna. Jag har därför skaffat en plats på spray.se eftersom denna tillåter php. Jag har dock inte i något av fallen kontroll över servern (det är inte min server).

 

När det gäller spelet så ansluter inte spelarna till servern som klienter. Det är endast en applet som körs och som laddas ner till spelarens lokala dator. Så hur får jag ett id för spelaren? Kanske kan spelaren mata in ett namn vid starten, som jämförs med namn i en lista i ngn databas eller textfil? När spelet är slut finns en variabel score som anger poängen.

 

Hur skulle ett skript se ut som tar emot poäng och id och som sedan jämför värden med en highscorelista och eventuellt uppdaterar den, för att sedan skicka highscorelistan till spelsidan som uppdateras dynamiskt?

 

Tack på förhand!

/Daniel

 

 

 

Link to comment
Share on other sites

-Patrik Johansson-

För att hämta information från din hidgscorefil kan du göra så här:

URL url = new URL("http://www.chalmers.se");
URLConnection con = url.openConnection();
BufferedReader reader = new BufferedReader(new InputStreamReader(con.getInputStream()));
String data = "";
while((data = reader.readLine()) != null) {
    //Här gör du något med raden du har läst in.
}

 

I whileloopen kan du exempelvis separera namn och poäng om filen har detta format eller något liknande:

poäng:namn

Separera detta gör du enklast genom att använda en StringTokenizer som delar upp strängen efter givna mönster.

 

StringTonkenizer token = new StringTokenizer(radenMedData, ":");
String name = token.nextToken();
int score = Integer.parseInt(token.nextToken());

: kan du ex ersätta mot ett blanksteg om du delar upp namn och poäng med blanskteg.

 

//Patrik J

"Not everything that counts can be counted, and not everything that can be counted counts."
- citat av Albert Einstein

 

Link to comment
Share on other sites

Här har jag skrivit några skript som borde lösa ditt problem, eller i alla fall hjälpa dig en bra bit på vägen. De har en lite annan struktur än jag först föreslog, delvis för att förenkla.

Skripten sparar poäng och namn til en fil, som det även ser till är sorterat med högsta poäng först, hämtar en lista, och skapar sessioner (som krävs för validering).

 

Man kan göra det lite snyggare med hjälp av användardefinierade matris-sorteringsfunktioner, men med tanke på att du är en nybörjare på PHP så har jag försökt hålla mig till relativt enkla funktioner och strukturer.

En sak du måste komplementera med är en begränsad levnadstid för sessionerna, annars kommer sessions-filen bli groteskt stor väldigt snabbt.

 

De värden du kan behöva ändra ligger högst upp i skriptet. Tänk även på att du måste ge skrivrättigheter till de filer och mappar som används.

 

Man kan även lösa krypteringen på lite snyggare och säkrare sätt, men dessa kräver en extra modul på webbservern, vilken jag inte vet om Spray har.

 

Jag har även för mig att Spray lägger till reklam på alla sidor, vilket kan bli ett problem när du vill hämta high score-listan. Det får du dock lösa på applet-sidan, vilket borde gå.

 

Det du alltså får implementera på applet-sidan är en krypteringsfunktion, vilken krypterar ID-numret med ett förbestämt salt. Titta som sagt i PHP-manualen efter funktionen crypt(), och sök lite på Java-sidor så borde du hitta en fungerande version där, helst med MD5-kryptering.

 

Spara poäng: http://min.server.se/spara.php?s=GsdfSE4rGs35gsdf3F&n=Daniel&p=7436

// Fil att där sessioner sparas
$sessFil = 'sessioner.txt';

// Filens namn och eventuell sökväg
$fil = 'highscores.txt';

// Poäng/namn-avdelare, samt ID/IP-avdelare
$avdelare = ':';

// Salt för kryptering (måste vara detsamma i appleten)
$salt = '$1$cdvigxofnchy';

// Namn och poäng att spara
$sparaNamn  = $_REQUEST['n'];
$sparaPoang = $_REQUEST['p'];
$kryptID    = $_REQUEST['s'];

// Kontrollera sessionen
$sessioner = @file($sessFil);
if (!is_array($sessioner)) exit; // Sessionsfilen kunde inte öppnas
$verifierad = false;
foreach ($sessioner as $sess) {
   $tmp = explode($avdelare, $sess);
   // Inte korrekt IP, eller inte ett giltigt ID
   if ($tmp[1] != $_SERVER['REMOTE_ADDR'] || crypt($tmp[0], $salt) != $kryptID) continue;
   $verifierad = true;
   break;
}

// Inte verifierad session?
if (!@$verifierad) exit;

// Hämta befintliga poäng
$poang = @file($fil);
if (!is_array($poang)) $poang = array();

// Leta upp rätt ställe att stoppa in poängen på
$i = 0;
foreach ($poang as $tmp)
{
$tmpPoang = explode($avdelare, $tmp);
if ($tmpPoang[0] < $_REQUEST['p']) break;
$i++;
}

// Stoppa in poängen i matrisen
array_splice($poang, $i, 0, $sparaPoang . $avdelare . $sparaNamn . "\n");

// Öppna fil för skrivning
$fp = @fopen($fil, 'w');

// Filen kunde öppnas; spara alla data
if ($fp)
{
foreach ($poang as $tmp) fwrite($fp, $tmp);
}

// Stäng filen
fclose($fp);

Hämta poäng: http://min.server.se/lista.php

// Filens namn och eventuell sökväg
$fil = 'highscores.txt';

// Skriv ut hela filen
readfile($fil);

Skapa en ny session: http://min.server.se/session.php

// Fil att spara ID-nummer osv i
$fil = 'sessioner.txt';

// ID/IP-avdelare
$avdelare = ':';

// Skapa ett unikt, slumpmässigt  ID-nummer
$id = md5(uniqid(rand(), true));

// Spara sessionen
$fp = fopen($fil, 'a');
fwrite($fp, $id . $avdelare . $_SERVER['REMOTE_ADDR'] . "\n");

// Returnera id-numret
echo $id;

 

Link to comment
Share on other sites

Aha... det börjar så långsamt klarna... har provat följande utan framgång... var går det snett (jag har lagt krypteringen på hyllan tills jag ser att det överhuvudtaget fungerar)?

 

//I FILEN highscores.txt på http://min.server.se'>http://min.server.se

 

Daniel:45

Kurt:40

etc...

 

Filen har getts skrivrättigheter!

 

//I FILEN spara.php på http://min.server.se

 

 

$fil = 'highscores.txt';

 

 

$avdelare = ':';

 

 

 

 

$sparaNamn = $_REQUEST['n'];

$sparaPoang = $_REQUEST['p'];

 

 

 

 

 

$poang = file($fil);

if (!is_array($poang)) $poang = array();

 

 

$i = 0;

foreach ($poang as $tmp)

{

$tmpPoang = explode($avdelare, $tmp);

if ($tmpPoang[0] < $_REQUEST['p']) break;

$i++;

}

 

array_splice($poang, $i, 0, $sparaPoang . $avdelare . $sparaNamn . "\n");

 

 

$fp = fopen($fil, 'w');

 

 

if ($fp)

{

foreach ($poang as $tmp) fwrite($fp, $tmp);

}

 

 

fclose($fp);

 

 

//I en testapplet

 

public class HighScoreTest extends JApplet {

 

public void init()

{

try

{

URL ur1 = new URL ("http://www.anst.uu.se/dapdo451/PHPTEST/spara.php?n="Daniel"&amp;p="30");

 

URLConnection uc = ur1.openConnection();

uc.setDoOutput( true );

 

 

}

catch(MalformedURLException mue) {

System.out.println("Illegal URL: " + mue);

} catch(IOException ioe) {

System.out.println("IOException: " + ioe);

} catch(Exception e) {

System.out.println("Error: " + e);

}

 

 

}

 

 

}

 

När jag provkör appleten och sedan tar en titt på highscore.txt så har inget hänt med denna...

 

Måste jag ansluta till filen genom att ange ngt lösenord och användarnamn eller så? Eller vad går snett?

 

Link to comment
Share on other sites

En sak jag ser med en gång är URLen du försöker öppna.

Det är möjligt att det är Eforum som konstrat till den, vilket det gör ibland, men du har skrivit:

"http://www.anst.uu.se/dapdo451/PHPTEST/spara.php?n="Daniel"&amp;p="30"

 

Det ska såklart vara:

"http://www.anst.uu.se/dapdo451/PHPTEST/spara.php?n=Daniel&p=30"

 

För att skicka med speciella värden i en GET-URL, så måste du koda om dem. Detta görs i PHP med rawurlencode() och i JavaSkript med escape(), men i Java vet jag inte. Leta efter en funktion som konverterar exempelvis mellanslag till "%20".

 

Link to comment
Share on other sites

Nu testade jag även att öppna sidan, och märkte då att du inte ens verkar ha en PHP-kompilator installerad, då jag får upp skriptet, och inte den exekverade koden.

 

Kör du verkligen på en server med PHP installerat?

 

Link to comment
Share on other sites

Hej! Provade att köra på samma server som spelet ligger på men inser att jag nog får flytta över till sprays... För min server hittade jag (angående PHP):

 

"Vissa av dessa funktioner är av säkerhetsskäl inte tillgängliga på WWW-hotellet; det gäller exempelvis funktioner för programexekvering, hantering av filsystem och liknande."

 

Misstänker att det kan vara boven i dramat... testar med spray och återkommer.. =) Men bör upplägget ovan fungera som jag har tänkt, eller är jag ute och cyklar i min PHP-okunnighet... =)

 

Link to comment
Share on other sites

-Patrik Johansson-

Så här skulle nog javakoden kunna se ut:

[color="#006400"]
URL url = new URL("http://www.adress.com/index.php?letter=e");
HttpURLConnection con = (HttpURLConnection)url.openConnection();
con.setRequestMethod("GET");
[/color]

 

För att fixa konvertering kan du utföra detta på URLen ifråga:

[color="#ff0000"]
URL url = new URL(URLEncoder.encode("den aktella urlen","UTF-8");
[/color]

 

//Patrik J

"Not everything that counts can be counted, and not everything that can be counted counts."
- citat av Albert Einstein

 

Link to comment
Share on other sites

Jag kan i alla fall köra följande utan problem på samma server i form av en test.php fil:

 

<html><head></head></html>

<body>

 

<?php

/* counter */

$datei = fopen("countlog.txt","r"); //opens countlog.txt to read

$count = fgets($datei,1000);

fclose($datei);

$count=$count + 1 ;

echo "<CENTER><FONT SIZE=\"3\" FACE=\"arial, verdana, helvetica\">you are vistor

 

no.</FONT></CENTER>" ;

echo "<CENTER><FONT SIZE=\"3\" FACE=\"arial, verdana, helvetica\">$count</FONT></CENTER>" ;

echo "\n<br>" ;

$datei = fopen("countlog.txt","w"); // opens to write and deletes the old count

fwrite($datei, $count);

fclose($datei);

?>

 

</body>

</html>

 

Så det borde inte vara några problem... skumt skumt... kanske jag gör fel i Java-appleten?

 

Link to comment
Share on other sites

Då kanske du bara har glömt att lägga till <?php precis i början av filen? Det måste du ju göra...

 

<?php

 

/* phpkod här */

 

?>

 

Link to comment
Share on other sites

=) Du har så rätt... ingen dålig nybörjartabbe va... =) Om jag nu anropar php-scriptet med

 

http://www.minserver.se/spara.php?n=Daniel&p=50

 

så sparas poängen i highscorefilen. Enda problemet är att highscorefilen får följande utseende:

 

70:Daniel

60:Kurt

60:Kurt

30:Daniel

20:Kurt

 

Hmm... skumt... nu ser den ju ut som den ska... i filen på servern när jag öppnar och läser den i WS_FTP ser den ut som

 

70:DanielFYRKANT60:KurtFYRKANT30:Daniel

20:Kurt

 

men "FYRKANTERNA" kanske bara markerar radslut eller nåt... hur blir det om jag läser in textfilen rad för rad?

 

Tusen tack för all hjälp förresten! Nu börjar jag se ett ljus i tunneln. Nu blir nästa steg att försöka förstå vad du pysslade med tidigare med sessioner och kryptering... =)

 

Link to comment
Share on other sites

Ville bara säga tack till er som hjälpt till (och i synnerhet Cariad). Nu har jag äntligen fått det att fungera som jag tänkt mig! Tusen tack för all hjälp!

/Daniel

 

Link to comment
Share on other sites

Archived

This topic is now archived and is closed to further replies.

×
×
  • Create New...