Du må være registrert og logget inn for å kunne legge ut innlegg på freak.no
X
LOGG INN
... eller du kan registrere deg nå
Dette nettstedet er avhengig av annonseinntekter for å holde driften og videre utvikling igang. Vi liker ikke reklame heller, men alternativene er ikke mange. Vær snill å vurder å slå av annonseblokkering, eller å abonnere på en reklamefri utgave av nettstedet.
  2 1039
Jeg har en nettside som henter ut en tabell fra en ekstern url. Denne tabellen blir hentet med PHP og file_get_contents($url); + en funksjon som henter ut kildekoden mellom spesifikke tager. Jeg får derfor en variabel som inneholder kildekoden til den eksterne tabellen, og som jeg igjen echoer på min side.

Hele poenget med min nettside, er å vise tabelldataen på en ryddigere måte. For å endre på tabelldesignet har jeg laget en egen css-fil hvor jeg benytter class-navnene som allerede finnes i tabellen, men enkelte steder må jeg endre selve koden til tabellen (f.eks. må jeg endre på HREF-verdiene flere steder, siden disse lenker til det eksterne domenet). Jeg har derfor i PHP-koden flere kodesnutter (str_replace/preg_replace) som erstatter diverse tekst i tabellkoden.

Selv om dette høres ut som ganske så skitten kode, fungerer det overraskende greit. Det er nå problemet mitt dukker opp: Siden laster sakte. Veldig sakte. Og det er nok hovedsaklig fordi de fleste av cellene fra den eksterne nettsida inneholder brukernavn. På min nettside vises derimot det ekte navnet, og for å få til dette benytter jeg meg av:

Kode

$url = preg_replace('/\bBRUKERNAVN\b/', 'EKTE NAVN', $url);
Dette fungerer jo for så vidt, men når det er snakk om over 10 000 slike preg_replace, skjønner man at siden laster ekstremt tregt. Det er snakk om cirka 20 brukernavn i hver tabell (kommer ny tabell fra den eksterne nettsiden daglig), men de 20 brukernavnene kan altså være hentet tilfeldig fra de 10 000 brukernavnene i lista jeg har.


TL;DR
Mitt spørsmål er da; går det an å legge de 10 000 brukernavnene inn i en MySQL-database, for deretter å kunne hente ut kun de 20 relevante brukernavnene? Altså at PHP-siden min tar verdiene fra tabellcellene, spør i databasen om BRUKERNAVN finnes, får svar tilbake om at EKTE NAVN er det ordentlige navnet til BRUKERNAVN, for deretter å sette dette ekte navnet som ny verdi i den respektive tabellcellen? På den måten vil i hvert fall lastetiden senkes betraktlig!

Kan legge til at jeg ikke er stødig i MySQL-programmering, men jeg vet hvordan jeg oppretter en database og legger inn data, samt å koble til en database fra PHP. Er for så vidt ikke veldig dyktig i PHP heller, men der skjønner jeg i hvert fall syntaksen nokså bra og klarer som oftest å søke meg fram til det meste. Så om noen vet en løsning på problemet mitt, hadde det vært fint om en eventuell MySQL-kode var nokså "klipp og lim" - eventuelt med et godt pekepinn om hvordan jeg kan få løst det selv.
Sist endret av zorro; 4. november 2013 kl. 16:35.
Før vi starter: Jeg har valgt noen lettvinte løsninger for å holde koden forståelig. Dette kan selvsagt gjøres mye mer gjennomført og effektivt, men da blir jeg nesten nødt til å teste koden før jeg poster

Du nevner ikke om du alltid henter dataen fra den samme URLen. Hvis så er tilfellet, så ville jeg ikke kalt file_get_contents ifra php-scriptet som brukeren benytter. Dette øker load time, belastning på din server, belastning på servern til den eksterne URLen, og gjør at din side går ned dersom den andre siden skulle bli overbelasta.

Dersom det alltid er det samme datasett-utvalget (samme listen over stash) som skal vises, lag et separat php-script som du kaller én gang i minuttet (elns). Scriptet henter ut alle radene fra tabellen og setter det inn i en MySQL-table i databasen din. Når brukeren så skal se din uber-awesome versjon av siden så kan alt hentes fra din lokale base og alt sparker langt mer ræv.

La oss si at tabellen på den eksterne siden har 4 felter: dato, brukernavn, rangering og penger. Databasen din vil ha en tabell som heter tabelldata med fem felter: id, dato, brukernavn, rangering og penger. Del opp hver row av tabellen på den eksterne siden i et php-array, slik at du kan gjøre noe slikt i en loop:

Kode

$id=$id+1
$dato=real_escape_string($verdier[0]);
$brukernavn=real_escape_string($verdier[1]);
$rangering=real_escape_string($verdier[2]);
$penger=real_escape_string($verdier[3]);
$result=mysql("insert into tabelldata values('$id', '$dato', '$brukernavn', '$rangering', '$penger')");
Poenget med id-feltet er at vi dermed kan lagre rekkefølgen som radene var i, slik at vi kan sortere på ID og vise vår tabell i samme rekkefølge.

Når brukeren vil vise den helgromme tabellen din kan hele kildekoden (index.php) være noe slikt:

Kode

<!DOCTYPE html><html><head>
	<meta charset="utf-8" />
	<title>supertabell</title>
	<style>
		html { background: #030; color: #8f8; }
	</style>
</head><body><table>
	<tr>
		<td>dato</td>
		<td>brukernavn</td>
		<td>ekte navn</td>
		<td>rangering</td>
		<td>penger</td>
	</tr>
<?php
$mi = new mysqli('127.0.0.1', 'brukernavn', 'passord', 'databasenavn') or die('faen');
$mi->set_charset('utf8') or die('server fuckup: æ ø å blir korrupt');
$q = "select * from tabelldata, navnetabell where brukernavn=username order by id";
$q = $mi->query($q) or die('kuk');
while ($row = $q->fetch_assoc())
{
	echo("<tr>" .
		 "<td>$row['dato']</td>" .
		 "<td>$row['username']</td>" .
		 "<td>$row['realname']</td>" .
		 "<td>$row['rangering']</td>" .
		 "<td>$row['penger']</td>" .
		 "</tr>");
}
?>
</table></body></html>
Nå, legg merke til at koden over viser både brukernavn og ektenavn i samme tabell... Dette bringer oss over til det egentlige spørsmålet ditt! Vi lager enda en tabell i databasen din, som heter navnetabell, med to felter: username og realname. Valget av engelsk gjør koden over lettere å forstå, da vi "binder sammen" tabellene idét vi henter ut informasjonen til tabellen din. Feltene dato, rangering og penger er fra database-tabellen tabelldata, mens vi også henter ut username og realname fra navnetabell.

Vi trenger også et nytt php-script som går igjennom listen over brukernavn på den eksterne siden. Listen er sikkert spredt over flere sider, så la scriptet hente ned alle sammen en etter en, hente ut listen på hver side og gå igjennom navnene, ett om gangen. Først sjekker du om navnet finnes i databasen din:

Kode

$results=mysql("select * from navnetabell where username='" .real_escape_string($brukernavn). "' limit 1")
Hvis denne spørringen ikke gir noen resultater (if (!$results)...) setter du inn brukeren i basen:

Kode

mysql("insert into navnetabell values('" .real_escape_string($brukernavn). "', '" .real_escape_string($ektenavn). "');") or die('fuckdamn shitcunts')
. Du kan egentlig hoppe over sjekken og gå rett på insert, hvis du setter opp names-tabellen til å ha feltet "username" til å være unikt, slik at databaasen stopper deg om du prøver å sette inn samma nickname flere ganger. Superlett å sette opp i phpMyAdmin for eksempel, så hvorfor ikke.

Actually, dette siste scriptet burde aller helst vært et skikkelig program, slik at du slipper bekymre deg for timeouts og får luksusen av å ha status-meldinger til deg selv underveis. Mer kontroll.

Flere tips, om du vil gjøre en skikkelig jobb: Les opp på foreign keys, slik at databasen forstår at det er en sammenheng mellom fletet brukernavn i tabelldata og username i navnetabell. Da går det fortere å generere siden din.

Lang post er lang, håper noe av det kommer til nytte. Ingenting er testa, så forvent noen feilmeldinger
Sist endret av tripflag; 4. november 2013 kl. 18:06.
Hjertelig takk, tripflag! Jeg ser det er mye nytt å sette seg inn i for meg, så dette blir utrolig lærerikt. Kommer med update etter jeg har fått jobbet en stund med eksemplene du kom med. Har allerede kommet et skritt nærmere målet!
Sist endret av zorro; 5. november 2013 kl. 09:27.