Kirjautuminen

Haku

Tehtävät

Keskustelu: Nettisivujen teko: Tietokannan rakenne foorumille

Sivun loppuun

MIB [31.05.2009 14:02:30]

#

Morjensta

Millainen rakenne kannattaisi antaa foorumin tietokannalle?

- tietokantani -
 - aiheen nimi - (Aiheen nimi aina oma taulu?)
  - lähettäjä - aika - viesti -
  - lähettäjä - aika - viesti -
 - aiheen nimi - (Aiheen nimi aina oma taulu?)
  - lähettäjä - aika - viesti -
  - lähettäjä - aika - viesti -

Tuo on ainoa tapa, jonka osaan näin hatusta vetää. Olisiko tämä myös mahdollinen?

- tietokantani -
 - viestit - (Yleinen taulu?)
  - aihe - lähettäjä - aika - viesti -
  - aihe - lähettäjä - aika - viesti -

Triton [31.05.2009 14:10:28]

#

En kyllä lähtisi luomaan jokaisella aiheelle omaa taulua, vaan loisin yhden taulun esim. "viestit" ja sinne sitten sarakkeet id,aiheen_nimi,viesti,pvm jne...

Edit.

Tietenkin voisi luoda yhden taulun aihee nimiä varten ja toisen viesteille ja siellä viestitaulussa jokaiselle tietueelle annetaan aihetta vastaava id...

Näin:

taulu: aiheet

+-----------+--------------+
|    id     | aiheen_nimi  |
+-----------+--------------+
|    1      |   Eka aihe   |
+-----------+--------------+


taulu: viestit

+-----------+--------------+-----------+
|    id     |    aihe_id   |   viesti  |
+-----------+--------------+-----------+
|    1      |       1      | viesti    |
+-----------+--------------+-----------+

MIB [31.05.2009 14:14:01]

#

Triton kirjoitti:

En kyllä lähtisi luomaan jokaisella aiheelle omaa taulua, vaan loisin yhden taulun esim. "viestit" ja sinne sitten sarakkeet id,aiheen_nimi,viesti,pvm jne...

Eli tämä jälkimmäinen? Minustakin olisi kyllä tyhmää lähteä tekemään jokaiselle aiheelle omaa taulua. Eikös tämä vaan hidastaisi kun on paljon tietoa?

Antti Laaksonen [31.05.2009 14:17:23]

#

Järkevä ratkaisu on käyttää kahta taulua: yhdessä ovat aiheet, toisessa ovat viestit (eli juuri Tonin esittelemä tapa). Nyrkkisääntö tietokannan suunnittelussa on, että taulujen määrä ei kasva, kun tietokantaan lisätään tietoa.

Triton [31.05.2009 14:19:28]

#

Antti Laaksonen kirjoitti:

Järkevä ratkaisu on käyttää kahta taulua: yhdessä ovat aiheet, toisessa ovat viestit (eli juuri Tonin esittelemä tapa). Nyrkkisääntö tietokannan suunnittelussa on, että taulujen määrä ei kasva, kun tietokantaan lisätään tietoa.

Itsekin kun mietin tarkemmin, niin näinpä tämä taitaa olla...

MIB [31.05.2009 14:22:22]

#

Antti Laaksonen kirjoitti:

Järkevä ratkaisu on käyttää kahta taulua: yhdessä ovat aiheet, toisessa ovat viestit (eli juuri Tonin esittelemä tapa). Nyrkkisääntö tietokannan suunnittelussa on, että taulujen määrä ei kasva, kun tietokantaan lisätään tietoa.

Selvä, eikun rakentamaan sitten yksinkertaista foorumiani. :D

PS. Antti, Putkassa tälläin myös?

EDIT: Jos antaa aika sarakkeelle tyypin, niin laitetaanko INT vai DATE?
Ja noi ihan TEXT vaan?

trilog [31.05.2009 14:52:24]

#

MIB kirjoitti:

EDIT: Jos antaa aika sarakkeelle tyypin, niin laitetaanko INT vai DATE?
Ja noi ihan TEXT vaan?

DATE noista vaihtoehdoista paras (= ainut oikea).

MIB [31.05.2009 14:53:00]

#

trilog kirjoitti:

MIB kirjoitti:

EDIT: Jos antaa aika sarakkeelle tyypin, niin laitetaanko INT vai DATE?
Ja noi ihan TEXT vaan?

DATE noista vaihtoehdoista paras (= ainut oikea).

Selvä. Muutetaampa sitten.

EDIT: Jostain syystä forum tietokantaani ei saada yhteyttä, toisin sanoin pääsy mitätöidään: Access denied for user ''@'localhost' to database 'forum'
Koodia:

<?php
$yhteys = mysql_connect("localhost", "", "") or die(mysql_error());
mysql_select_db("forum") or die(mysql_error());

if ($yhteys)
echo "Kunnossa";
else echo "Epäkunnossa";

mysql_close($yhteys);
?>

Tuolla kyseisellä tietokannalla ei toimi, mutta test kannallani toimii. En ole mitään erikoista säätänyt tuohon forum kantaan.

EDIT2: Laitoin tunnukseksi root niin jo lähti toimimaan. Ei omalla serverillä ennen ole tarvinnut tuollaisia... :S

Antti Laaksonen [31.05.2009 15:22:09]

#

MIB kirjoitti:

PS. Antti, Putkassa tälläin myös?

Kyllä vain.

MIB kirjoitti:

Jos antaa aika sarakkeelle tyypin, niin laitetaanko INT vai DATE?

Tämä ei ole tärkeä valinta. Minä olen yleensä valinnut tyypin INT ja tallentanut siihen PHP:n aikaleiman.

MIB [31.05.2009 15:25:48]

#

Antti Laaksonen kirjoitti:

MIB kirjoitti:

PS. Antti, Putkassa tälläin myös?

Kyllä vain.

MIB kirjoitti:

Jos antaa aika sarakkeelle tyypin, niin laitetaanko INT vai DATE?

Tämä ei ole tärkeä valinta. Minä olen yleensä valinnut tyypin INT ja tallentanut siihen PHP:n aikaleiman.

Selvä. Näiden vastausten perusteella alan tekemään. :) Kiitos vastanneille!

trilog [31.05.2009 15:32:40]

#

Antti Laaksonen kirjoitti:

Tämä ei ole tärkeä valinta. Minä olen yleensä valinnut tyypin INT ja tallentanut siihen PHP:n aikaleiman.

Eikö TIMESTAMP -tietotyyppi ole tuota varten?

Antti Laaksonen [31.05.2009 16:02:34]

#

Aikaleima on kokonaisluku, joten tyyppi INT on minusta sopiva.

tsuriga [31.05.2009 16:08:46]

#

Syitä, miksi käyttää valmiita tietokannan aikatietotyyppejä:

Valmiit aikatietotyypit ovat siis mahdollisesti selkeyttämässä ja helpottamassa koodia sekä tietokannan rakennetta ja pitävät huolen mahdollisten sudenkuoppien välttämisestä — käytä siis niitä. Tässä ehkäpä DATETIME, koska halunnet varmaan myös kellonajan, jolloin viesti kirjoitettiin.

Olli [31.05.2009 16:30:41]

#

Kun saat softan valmiiksi, laitahan demoa tännekkin :)

MIB [31.05.2009 17:48:46]

#

PS. Muuten, miten tallennan ajan? Tulee vaan nollia tietokantaan viestiä kirjoittaessa.

EDIT: Että tuli jotain nollien tilalle, niin piti muuttaa aika sarakkeen muodoksi INT. Se tallentaa nyt ajan tätä luokkaa: 1243781366. Jos tuo on muuttujassa (kun luetaan viestiä) $lähetetty, ja luetaan näin:

<?php
$lähetetty = 1243781366;
echo date("d.m.Y H:i", $lähetetty)
?>

Toimiiko tälläinen?

MIB [31.05.2009 18:58:57]

#

MIB kirjoitti:

<?php
$lähetetty = 1243781366;
echo date("d.m.Y H:i", $lähetetty)
?>

Toimiiko tälläinen?

Joo, ton sain toimimaan, mutta, nyt tuli seuraava pulma. Miten käännän listan ympäri? Nyt uusin on alhaalla, kun kuuluisi toistapäin olla. Array_reverce vai oli array_revearce:lla menisi jos olisi tekstitiedostossa?

trilog [31.05.2009 19:29:34]

#

MIB kirjoitti:

Joo, ton sain toimimaan, mutta, nyt tuli seuraava pulma. Miten käännän listan ympäri? Nyt uusin on alhaalla, kun kuuluisi toistapäin olla. Array_reverce vai oli array_revearce:lla menisi jos olisi tekstitiedostossa?

ORDER BY ja DESC? Menee se tosin PHP:n puolellakin array_reversellä kun vain haet halutut tiedot taulukkoon (suosittelen kuitenkin ensimmäistä tapaa).

MIB [31.05.2009 19:36:05]

#

trilog kirjoitti:

ORDER BY ja DESC?

Ai niin joo! :D Unohdin tämän ihan kokonaan.

Metabolix [31.05.2009 19:49:11]

#

trilog kirjoitti:

MIB kirjoitti:

EDIT: Jos antaa aika sarakkeelle tyypin, niin laitetaanko INT vai DATE?
Ja noi ihan TEXT vaan?

DATE noista vaihtoehdoista paras (= ainut oikea).

Aikaleimaksi kylläkin DATETIME on DATEa parempi, koska DATE ei sisällä lainkaan kellonaikaa. Toisaalta TIMESTAMP on ehkä tässä tilanteessa paikallaan. Sen voi myös säätää taulua luodessa asettumaan tai myös päivittymään itse, jolloin esimerkiksi viestien lähetys- ja muokkausaikoja ei tarvitsisi itse koskaan asettaa, vaan ne tulisivat automaattisesti.

trilog [31.05.2009 19:53:32]

#

Metabolix kirjoitti:

Aikaleimaksi kylläkin DATETIME on DATEa parempi, koska DATE ei sisällä lainkaan kellonaikaa. Toisaalta TIMESTAMP on ehkä tässä tilanteessa paikallaan. Sen voi myös säätää taulua luodessa asettumaan tai myös päivittymään itse, jolloin esimerkiksi viestien lähetys- ja muokkausaikoja ei tarvitsisi itse koskaan asettaa, vaan ne tulisivat automaattisesti.

Totta, mutta huomioithan "noista vaihtoehdoista". :)

Olisihan minun toki pitänyt mainita tähän tarkoitukseen paras vaihtoehto, mutta en sitten tullut ajatelleeksi sen enempää.

MIB [31.05.2009 20:56:39]

#

trilog kirjoitti:

ORDER BY ja DESC

Miten tämä taas menikään?
SELECT * FROM viestit WHERE aihe_id = '$id' ORDER BY aika DESC
vai jotain muuta?

Triton [31.05.2009 20:58:52]

#

Juuri noin se toimii... Eli luonnollisesti tuo järjestää tietueet nousevassa järjestyksessä aika-sarakkeen mukaan.

MIB [31.05.2009 21:07:32]

#

Triton kirjoitti:

Juuri noin se toimii... Eli luonnollisesti tuo järjestää tietueet nousevassa järjestyksessä aika-sarakkeen mukaan.

Olisiko DESC uusin ensimmäisenä (viimeiseksi lähetetty) vai ASC?

Antti Laaksonen [31.05.2009 21:11:17]

#

ASC = pienimmästä suurimpaan
DESC = suurimmasta pienimpään

Uusin aika on suurin, eli oikea valinta on DESC.

MIB [31.05.2009 21:17:24]

#

Antti Laaksonen kirjoitti:

ASC = pienimmästä suurimpaan
DESC = suurimmasta pienimpään

Uusin aika on suurin, eli oikea valinta on DESC.

Kiitos, nyt toimii :)

Nyt olisi tämä muuten valmis, paitsi kaikki hienoudet puuttuu:
- Oma sivu
- Rekisteröinti (Tunnus on aina minun nimeni :P Tulee korjaus)
- Tilastot, mm. viestimäärät per keskustelu tms.

Voi kertoa, mitä voisin lisätä siihen.
Tuohon tilastot juttuun vielä sen verran, että olisi kiva tuo asuinpaikka juttu kartalla, mutta se on aikas vaikea tehdä. :D

EDIT: Nyt on todella lähellä, että itse aiheiden aloitus ja vastaaminen toimivat! Pari juttua silti kiikastaa: 1. Jos aiheeseen ei ole vastattu, aiheen alkuun tulostuu 3 mysql erroria. Tämän saan korjattua tarkistamalla onko vastausta käytten If -lausetta.
2. Yhteen aiheeseen voi vastata vain kerran. Olen huomannut saman ongelman ennenkin, mutta eri tilanteessa.

Tein tietokanta rakenteen seuraavasti:
Minulla on forum tietokanta, jossa on 3 taulua; aiheet, viestit ja vastaukset.
Aiheet tauluun tallentuu aiheiden otsikot.
Viestit tauluun tallentuu jokaisen aiheen aloitusviesti.
Vastaukset tauluun tallentuvat vastaukset joita sitten haetaan sinne tallennetun otsikon perusteella.

Sitten on myös nämä puutteet, mitkä aikaisemmin mainitsinkin, että ei voi muokata viestiä tms. Sen muokkaamisen saan tehtyä helposti.

PS. Onkohan minun ollut järkevää tehdä foorumi niin, että aisiin ei viitata ID:n perusteella vaan otsikolla? Eli, tämän alue.php?id=xxx onkin alue.php?aihe=Aiheen Nimi.

Antti Laaksonen [31.05.2009 22:09:05]

#

MIB kirjoitti:

Viestit tauluun tallentuu jokaisen aiheen aloitusviesti.
Vastaukset tauluun tallentuvat vastaukset joita sitten haetaan sinne tallennetun otsikon perusteella.

Aloitusviestien tallennus erilliseen tauluun voi olla aika turhaa. Jos kaikki viestit olisivat samassa taulussa, aloitusviestin tunnistaisi siitä, että sen lähetysaika on varhaisin.

MIB kirjoitti:

Onkohan minun ollut järkevää tehdä foorumi niin, että aisiin ei viitata ID:n perusteella vaan otsikolla?

Tässä voi muodostua ongelmaksi, jos kahdella aiheella on sama otsikko. Lisäksi kaikki merkit eivät voi esiintyä sellaisenaan sivun osoitteessa.

MIB [31.05.2009 22:15:16]

#

Antti Laaksonen kirjoitti:

MIB kirjoitti:

Onkohan minun ollut järkevää tehdä foorumi niin, että aisiin ei viitata ID:n perusteella vaan otsikolla?

Tässä voi muodostua ongelmaksi, jos kahdella aiheella on sama otsikko. Lisäksi kaikki merkit eivät voi esiintyä sellaisenaan sivun osoitteessa.

Kyllä, kaikki eivät voi esiintyä, mutta silloin korvaan nämä sallitulla merkillä ja muunnan ne tulostusvaiheessa takaisin. (Tulee kun ehditään)
Oli myös helpompaa tehdä se otsikon perusteella.
Jos on saman niminen aihe jo ennestään kun aihetta luodaan, koodi ei luo uutta aihetta vaan kirjoittaa viestin vanhaan aiheeseen. (Tarkoitus ainakin tulla)

<?php
$kysele2 = "SELECT * FROM vastaukset WHERE otsikko = '$otsikko'";

$hae = mysql_query($kysele2, $yhteys);
$vastaaja = mysql_result($hae, $i, "lähettäjä_id");
$aika2 = mysql_result($hae, $i, "aika");
$aikaa = date("d.m.Y H:i", $aika2);
$viestii = mysql_result($hae, $i, "viesti");
echo "<tr><td width=\"250\">Lähettäjä:<b> $vastaaja</b></td><td>Milloin: <b>$aikaa</b></td></tr>";

echo "<tr><td>$viestii<br><br></td></tr>";
?>

Miten tarkistetaan, onko tiedot haettavissa? if ($hae) ei vastaa samaa kuin 0 tässä tarkoituksessa.

Antti Laaksonen [31.05.2009 22:20:05]

#

MIB kirjoitti:

Miten tarkistetaan, onko tiedot haettavissa?

Funktiolla mysql_num_rows voi tarkistaa, kuinka monta riviä tietoa kysely nouti tietokannasta. Puuttuukohan yllä olevasta koodista silmukka? Tämä selittäisi sen, että vain yksi vastaus näkyy.

MIB [01.06.2009 08:37:32]

#

Antti Laaksonen kirjoitti:

MIB kirjoitti:

Miten tarkistetaan, onko tiedot haettavissa?

Funktiolla mysql_num_rows voi tarkistaa, kuinka monta riviä tietoa kysely nouti tietokannasta. Puuttuukohan yllä olevasta koodista silmukka? Tämä selittäisi sen, että vain yksi vastaus näkyy.

Kiitos, tietenkin se menee näin ;)

Metabolix [01.06.2009 09:41:16]

#

On käytännöllisempää hakea kokonainen rivi hakutuloksista vaikkapa mysql_fetch_assoc-funktiolla. Tämä myös palauttaa falsen, jos dataa ei ole saatavilla.

<?php
// Yritetään hakea rivi, ja jos sellainen vielä saadaan, jatketaan silmukkaa.
while ($rivi = mysql_fetch_assoc($hae)) {
  // Taulukossa ovat kätevästi kaikki hakutuloksen tiedot.
  $viesti = $rivi["viesti"];
}

MIB [01.06.2009 11:30:29]

#

Warning: session_start() [function.session-start]: Cannot send session cache limiter - headers already sent (output started at C:\xampplite\htdocs\foorumi\ylaosa.php:9) in C:\xampplite\htdocs\foorumi\yla.php on line 1

Mitä tämä meinaa? Tuo ykkös rivi on tämän näköinen: <?php session_start();
Ei minun mielestä tuossa ole mitään väärin. Silti sanoo niin.

EDIT:
Lainaus toisesta keskustelusta:

Blaze kirjoitti:

Kristallipallo sanoo, että sulla on jotain HTML:ää ennen tuota. Laita tuo PHP-pätkä ihan ensimmäiseks. http://pp.kpnet.fi/blaze/codefaq/#headerssent

Näinhän oli taas käynyt, että oli turhaa tulostettu väärään paikkaan väärää tietoa.

MIB [01.06.2009 12:51:33]

#

XML-sivua ei voi näyttää
XML-syötettä ei voi näyttää, jos tyylisivu on XSL. Korjaa virhe ja valitse Päivitä tai yritä myöhemmin uudelleen.


--------------------------------------------------------------------------------

XML-asiakirjassa voi olla vain yksi ylätason elementti. Virhe resurssia http://192.168.0.105/foorumi/uusiaihe.php?alue=1 kä...

<b>Warning</b>:  Cannot modify header information - headers already sent by (output started at C:\xampplite\htdo...

Tämmöisen virheen näyttää. Koodit:

1. uusiaihe.php (Aiheen luontiin)

<?php include("yla.php");
$yhteys = mysql_connect("localhost", "root", "");
mysql_select_db("forum", $yhteys);

$alue = $_GET["alue"];
$viesti = $_POST["viesti"];
$otsikko = $_POST["otsikko"];

$aihe_id = $_GET["alue"];
$lähettäjä_id = $user['tunnus'];
$aika = time();

if ($alue == "1") {
$kysely = "INSERT INTO aiheet (aihe_id, otsikko) VALUES ('1', '$otsikko')";
$kysely2 = "INSERT INTO viestit (viesti_id, otsikko, aihe_id, lähettäjä_id, aika, viesti) VALUES ('1', '$otsikko', '1', '".$user['tunnus']."', '$aika', '$viesti')";
mysql_query($kysely, $yhteys);
mysql_query($kysely2, $yhteys);
header("Location: alue.php?id=1");
}
mysql_close($yhteys);
?>

2. yla.php (Asetuksia)

<?php session_start();
include("config.php"); //muuta config.php:n polku oikeaksi
//avataan yhteys tietokantaan
$lnk = mysql_connect($db_server,$db_user,$db_passwd) or die ("Yhteys tietokantaan epäonnistui");
mysql_select_db($db_db,$lnk) or die ("Tietokannan valitseminen epäonnistui");

//käyttäjä on oletuksena false. Älä varsinkaan poista, ellet tiedä mitä teet :)
$user = false;


/* SISÄÄNKIRJAUTUMINEN */
if(isset($_POST['tunnus']) && isset($_POST['salasana'])){

   //muuttujat turvallisesti talteen
   $tunnus = get_magic_quotes_gpc() ? $_POST['tunnus'] : mysql_real_escape_string($_POST['tunnus']);
   $salasana = get_magic_quotes_gpc() ? $_POST['salasana'] : mysql_real_escape_string($_POST['salasana']);
   $salasana = md5($salasana);

   //luodaan käyttäjäkohtainen uniikki id
   $istuntotunnus = md5(uniqid(""));
   //lisätään istunto tietokantaan käyttäjän tietoihin
   mysql_query("UPDATE {$tbl_users}
   SET istunto = '{$istuntotunnus}'
   WHERE tunnus = '{$tunnus}'
   AND salasana = '{$salasana}'",$lnk) or die (mysql_error());
   //jos lisättyjä rivejä on yksi, kirjautuminen onnistui
   if(mysql_affected_rows($lnk) == 1){
      //laitetaan sessioon talteen istuntotunnus
      $_SESSION['log_key'] = $istuntotunnus;
      //takaisn edelliselle sivulle. Parempiakin tapoja on
      header("Location: ".isset($_SERVER['HTTP_REFERER']) ? $_SERVER['HTTP_REFERER'] : "index.php");
   }
}

/* ULOSKIRJAUTUMINEN */
if(isset($_REQUEST['logout'])){

   unset($_SESSION['log_key']);
   session_destroy();

}


/* KÄYTTÄJÄN TUNNISTUS */
if(isset($_SESSION['log_key'])){

   //HAETAAN KÄYTTÄJÄN TIEDOT
   $sql = "SELECT
   id,
   tunnus,
   DATE_FORMAT(last_load,'%d.%m.%y %h:%i:%s') AS last_load
   FROM {$tbl_users}
   WHERE istunto = '".mysql_real_escape_string($_SESSION['log_key'])."'";
   $sql = mysql_query($sql,$lnk);
   if($sql && mysql_num_rows($sql) == 1){
     //käyttäjä tunnistettu, kaikki kunnossa
      $user = mysql_fetch_assoc($sql);
      //nyt käyttäjän tiedot ovat mukavasti $user[]-taulukossa
      //esim. käyttäjän id löytyy $user['id'] ja tunnus $user['tunnus']

      //lisätään vielä käyttäjän viimeisestä sivunlatauksesta aikaleima
      mysql_query("UPDATE {$tbl_users} SET
      last_load = NOW()
      WHERE id = ".$user['id'], $lnk);

   }


}

/*

   TÄSTÄ ETEENPÄIN VOI SOVELTAA NIIN PALJON KUIN JAKSAA.
   JOS KÄYTTÄJÄ ON SISÄLLÄ, VOIDAAN SE TODETA YKSINKERTAISESTI
   TUTKIMALLA $user-TAULUKKOA:
      if($user){
         //tee jotain
      }else{
         //tee jotain muuta
      }
   YLLÄ HAETTIIN KANNASTA KÄYTTÄJÄN id, tunnus JA VIIMEISIN
   SIVUNLATAUS, JOTKA NIINIKÄÄN LÖYTYVÄT $users-taulukosta:
   $user['id'], $user['tunnus'] ja $user['last_load'],

*/

// Tekee käyttäjille taulun MySQL:ään. Voi poistaa ekan sivunlatauksen jälkeen.
mysql_query("CREATE TABLE IF NOT EXISTS `{$tbl_users}` (
  id int(11) NOT NULL auto_increment,
  tunnus varchar(50) default NULL,
  salasana varchar(32) default NULL,
  email varchar(60) default NULL,
  last_load timestamp(14) NOT NULL,
  istunto varchar(32) default NULL,
  PRIMARY KEY  (id),
  UNIQUE KEY istunto (istunto)
)",$lnk);
echo '<?xml version="1.0" encoding="iso-8859-1"?>';
?>

Missä mättää? :S

EDIT: Tuon XML errorin sain poistamalla yla.php:n lopusta tuon echon. Nyt siis toimii, ainakin melkein.

Warning: Cannot modify header information - headers already sent by (output started at C:\xampplite\htdocs\foorumi\yla.php:99) in C:\xampplite\htdocs\foorumi\uusiaihe.php on line 18

Tätä en saa kyllä millään toiseen paikkaan, tai mitään sen edestä pois :S

Metabolix [01.06.2009 14:27:43]

#

Rivi 99 on ainakin tuossa koodissa viimeinen rivi, joten luultavasti tiedostosi lopussa on ylimääräisiä rivinvaihtoja PHP-koodin ulkopuolella eli sulkutagin ?> jälkeen. Voit korjata asian ottamalla sulkutagin pois koodin lopusta (tämä ei ole syntaksivirhe), jolloin tiedosto käsitellään PHP:nä loppuun asti eikä mitään rivinvaihtoja tulosteta.

MIB [01.06.2009 14:45:48]

#

Metabolix kirjoitti:

Rivi 99 on ainakin tuossa koodissa viimeinen rivi, joten luultavasti tiedostosi lopussa on ylimääräisiä rivinvaihtoja PHP-koodin ulkopuolella eli sulkutagin ?> jälkeen. Voit korjata asian ottamalla sulkutagin pois koodin lopusta (tämä ei ole syntaksivirhe), jolloin tiedosto käsitellään PHP:nä loppuun asti eikä mitään rivinvaihtoja tulosteta.

Hee, nyt toimii :)
Nyt sivulla on seuraavat asiat:
- Kirjautuminen ja rekisteröitymnen:
Kirjautuneena voi ainoastaan luoda aiheen, vastata aiheeseen, katsella jäseniä tai niiden profiileja.
- Oma sivu:
Omalla sivulla on oikea nimi, email, kotisivut, paikkakunta jne..

Tuohon vielä sitten ne perusominaisuudet kuten viestien lähetys tms.
Vielä joitain hienouksia puuttuu.

EDIT: Nyt tarvitsisin seuraavan laisen jutun. Tämä on hiukan ehkä vaikea minun tehdä, kun en viittaa mihinkään ID numeroilla, paitsi käyttäjiin...
Pitäisi saada sellainen koodi, joka tarkistaa, että jos on yli 20 viestiä, niin seuraava tulee toiselle sivulle.

Nyt kun en ole pahemmin mitään ihmeellistä sinne tehnyt, niin voisin muokata niin, että viitattaisiinkin ID:llä eikä nimellä. En vain osaa laskea sitä ID numeroa.
Pitäisi kahdesta taulusta (viestit ja vastaukset) lukea rivimäärä ja lisätä lukuun 1 kun vastataan/luodaan aihe.

-MIB

Sami [01.06.2009 15:46:38]

#

Ihan hyvin voit sille tietokannalle sanoa montako tulosta haluat sieltä ulos ja mistä kohdasta tulosjoukkoa LIMIT-avainsanan avulla. Ensimmäinen luku on offset (monennesko rivi on ensimmäinen mukaan otettava, indeksointi alkaa nollasta) ja jälkimmäinen on montako riviä otetaan mukaan.

SELECT halutut, sarakkeet FROM taulu WHERE ketju = mitäonkaan ORDER BY aikaleima LIMIT (sivunumero * 20), 20;

map_ [01.06.2009 15:48:29]

#

Samin tapa on oikea. Se vaatii, että ketjutauluun on talletettu viimeisimmän uusimman viestin aikaleima, mikä on hyvä tapa tehdä tämä. Onnistuu tämä niinkin, että aika on tallennettu vain viestitauluun, mutta silloin kyselystä tulee monimutkaisempi ja (suurilla viestimäärillä) hitaampi.

Toinen juttu: uusiaihe.php:ssä unohdat käyttää mysql_real_escape_string:iä.
Lisäksi nuo kaksi inserttiä pitäisi oikeasti tehdä transaktiossa. Näiden kahden virheen tiimoilta tekee mieli linkata tähän.

TeNDoLLA [01.06.2009 16:00:08]

#

Taitaa olla niin, että se nopeus ero on aika marginaalinen jos käytetään LIMITtiä rajoittamaan hakutuloksien määrää joka tapauksessa.

MIB [01.06.2009 16:20:53]

#

Selvä, entä tämä ID numero juttu jokaiselle viestille?
alue.php?aihe=Aiheen nimi sijasta otettaisiinkin alue.php?aiheid=aiheennumero&viestiid­=viestinumero

Miten kuuluisi tehdä?

Metabolix [01.06.2009 16:22:24]

#

Mikä siinä on ongelmana? Olethan jo käyttänyt ID:tä käyttäjille ihan oikein.

MIB [01.06.2009 16:24:18]

#

Käyttäjien rekisteröityminen ja kirjautuminen perustuu tähän koodivinkkiin.

TeNDoLLA [01.06.2009 16:43:24]

#

Teet niin, että saat aiheen numeron php:ltä, kun aihetta klikataan ja haet kannasta viestit, jotka liittyy kyseiseen aiheeseen (aihe_id:seen) ja tulostat ne.

MIB [01.06.2009 16:47:01]

#

TeNDoLLA kirjoitti:

Teet niin, että saat aiheen numeron php:ltä, kun aihetta klikataan ja haet kannasta viestit, jotka liittyy kyseiseen aiheeseen (aihe_id:seen) ja tulostat ne.

Kyllä osaan tehdä tuon, mutta kun viittaan sisältöön nimen perusteella, niin en käyttänyt aikaa tallentaakseni aihe_id:tä ja viesti_id:tä oikein. Kummankin arvot ovat aina 1.

TeNDoLLA [01.06.2009 16:48:35]

#

Siinä tapauksessa sulla on kannan uudelleen suunnittelua edessä. Ainakin suosittelisin sitä, koska aiheen nimen perusteella ei ole kovin järkevää viitata jo senkin takia, että nimi voi olla sama. Millanen sulla on tällä hetkellä se tietokantarakenne ?


kayttajat
----------------------------
kayttaja_id (auto_increment)
kayttaja
passu


aiheet
----------------------------
aihe_id (auto_increment)
aihe
aika
kayttaja_id (viittaa kayttajat tauluun)

viestit
----------------------------
viesti_id (auto_increment)
viesti
aika
aihe_id (viittaa aiheet tauluun)
kayttaja_id (viittaa kayttajat tauluun)

Jotenkin näin pikaisesti sommiteltuna alkaisin itse tekemään tuota. Tässä tapauksessa aiheen ja viestien postaajat haetaan kayttaja_id:n perusteella kayttajat taulusta. Ja aiheeseen liitetään siihen kuuluvat viestit aihe_id:n perusteella.

EDIT: Tätä samaa tyyliä onkin jo viljelty aikaisemminkin tässä threadissa Tonin ja Antin toimesta.

MIB [01.06.2009 17:01:01]

#

Ajattelin jotain tälläistä:

aiheet: (Jokaisen aiheen nimi ja id tänne)
 aihe_id (Id, ekalle aiheelle 1, tokalle 2 jne...)
 otsikko (Aiheen otsikko)

viestit: (Jokaisen aiheen ensimmäinen viesti täällä)
 aihe_id (Tämän perusteella tulostetaan ensimmäinen viesti saman numeroiseen aiheeseen)
 viesti_id (Tätä tarvitaan muokkaamiseen ja poistoon tms.)
 otsikko (Aiheen otsikko)
 lähettäjä_id (Ei varsinaisesti id, vaan nimi, esim Rocceri)
 aika (xxxxxxxxxx aika)
 viesti (käyttäjän lähettämä viesti, ensimmäinen aiheessa)

vastaukset
 lähettäjä_id (Lähettäjän tunnus)
 otsikko (Aiheen otsikko)
 aika (xxxxxxxxxx aika)
 viesti (viesti)

Näin on nykyään, mutta nyt viittaan tuolla otsikolla, kun pitäisi id:llä..

Saan tehtyä aika helposti, jos tiedän miten voin laskea taulusta rivien määrä (mysql_num_rows?) ja tulostaa määrän. Saan väännettyä tuosta sitten kaikki tarvittavat..

Metabolix [01.06.2009 17:16:03]

#

Katselepa sitä käyttäjätaulua ja tutustu AUTO_INCREMENT-määreeseen hieman tarkemmin. Sitä käyttäessä vasta lisätyn id:n saa mysql_insert_id-funktiolla. Mitään id:tä ei pidä luoda itse epämääräisillä viritelmillä, kun kerran on valmiit välineet juoksevan numeroinnin tekoon.

MIB [01.06.2009 17:17:33]

#

Metabolix kirjoitti:

Katselepa sitä käyttäjätaulua ja tutustu AUTO_INCREMENT-määreeseen hieman tarkemmin. Sitä käyttäessä vasta lisätyn id:n saa mysql_insert_id-funktiolla. Mitään id:tä ei pidä luoda itse epämääräisillä viritelmillä, kun kerran on valmiit välineet juoksevan numeroinnin tekoon.

Luoko tämä ID:t 1, 2, 3, 4 jne. vai tuommoista hirveää siansakaa?

trilog [01.06.2009 17:42:19]

#

MIB kirjoitti:

Luoko tämä ID:t 1, 2, 3, 4 jne. vai tuommoista hirveää siansakaa?

Mitä siansaksaa? ID:t alkavat ykkösestä ja kasvavat aina sitä mukaa kun uusi tietue tulee. Samaa ID:tä mikään toinen tietue ei saa, vaikka tietoja poistettaisiin välistä. ID:n on tarkoitus olla tietueen yksilöivä numero, eikä sitä ole mitään syytä pitää esimerkiksi aiheiden määrän kanssa samana.

MIB [01.06.2009 17:47:09]

#

trilog kirjoitti:

MIB kirjoitti:

Luoko tämä ID:t 1, 2, 3, 4 jne. vai tuommoista hirveää siansakaa?

Mitä siansaksaa? ID:t alkavat ykkösestä ja kasvavat aina sitä mukaa kun uusi tietue tulee. Samaa ID:tä mikään toinen tietue ei saa, vaikka tietoja poistettaisiin välistä. ID:n on tarkoitus olla tietueen yksilöivä numero, eikä sitä ole mitään syytä pitää esimerkiksi aiheiden määrän kanssa samana.

Hups, mun moka. Tota koodia mitä testailin, niin se md5 -cryptasi sen...

Siis, asetan taulun näin? (Aiheet taulu)

mysql_query("CREATE TABLE aiheet (id INT NOT NULL AUTO_INCREMENT, otsikko TEXT) VALUES ('', '$otsikko')");

tsuriga [01.06.2009 18:00:15]

#

Md5 ei ole kryptausalgoritmi, vaan hash-algoritmi.

MIB [01.06.2009 18:04:04]

#

tsuriga kirjoitti:

Md5 ei ole kryptausalgoritmi, vaan hash-algoritmi.

Kirjoitusvirhe.. Tai ajatusvirhe tarkemmin.
Mutta, miten oikeasti teen tämän ID jutun?

Triton [01.06.2009 19:24:47]

#

MIB kirjoitti:

Mutta, miten oikeasti teen tämän ID jutun?

Siis, mitä epäselvää tuossa enää on. Eli kun luot sen taulun annat sille id-sarakkeelle sen auto_increment lisämääreen. Sitten kun luot uuden tietueen, niin teet sen vaikka näin:

INSERT INTO aiheet (id,otsikko) VALUES ('','Otsikko')

EDIT.

En pistä päätäni pantiksi, mutta tuo käyttämäsi kyselynrakenne
näyttää epäilyttävältä...

MIB kirjoitti:

Siis, asetan taulun näin? (Aiheet taulu)

mysql_query("CREATE TABLE aiheet (id INT NOT NULL AUTO_INCREMENT, otsikko TEXT) VALUES ('', '$otsikko')");

Eli taulun luonnin yhteydessä älä anna sille mitään muita arvoja, paitsi mahdolliset oletusarvot (joiden käytön mahdollisuudesta en tiedä)... Mutta perustietuetta ei kyllä CREATE TABLELLA tehä...

Grez [01.06.2009 19:59:07]

#

Triton kirjoitti:

INSERT INTO aiheet (id,otsikko) VALUES ('','Otsikko')

Joissakin kannoissa tuo voi jopa toimia (toisissa antaa virheen jos ID on autoincrement ja/tai numero) mutta tyylikkäämmin seuraavasti

INSERT INTO aiheet (otsikko) VALUES ('Otsikko')

Triton [01.06.2009 20:04:54]

#

Grez kirjoitti:

Triton kirjoitti:

INSERT INTO aiheet (id,otsikko) VALUES ('','Otsikko')

Joissakin kannoissa tuo voi jopa toimia (toisissa antaa virheen jos ID on autoincrement ja/tai numero) mutta tyylikkäämmin seuraavasti

INSERT INTO aiheet (otsikko) VALUES ('Otsikko')

Itselläni tuo on aina toiminut kun MySQL:llää olen käyttänyt, mutta täytyy tehdä seuraavalla kerralla tehdä kertomallasi tavalla...

MIB [01.06.2009 20:07:12]

#

Triton kirjoitti:

Siis, mitä epäselvää tuossa enää on.

En tarkoita tätä. Pitäisi siis nyt ensin tehdä tuo taulu... :p

mysql_query("CRATE TABLE aiheet (
id INT NOT NULL AUTO_INCREMENT,
otsikko TEXT,
PRIMARY KEY  (id)
)");

Noin en saanut toimimaan. Miten kuuluu luoda siis taulukko, jossa on id ja otsikko?

TeNDoLLA [01.06.2009 20:09:02]

#

Alla on tuosta mun ehdottamasta rakenteesta taulujen luonti koodit, vähäsen testi dataa inserttien muodossa ja lopuksi vielä esimerkki kyselyt miten niitä datoja voi mm. hakea tuolta sitten php:lla työstettäväksi.

CREATE TABLE `kayttajat` (
	`kayttaja_id` int(11) unsigned NOT NULL AUTO_INCREMENT,
	`kayttaja_nimi` varchar(255) NOT NULL,
  PRIMARY KEY  (`kayttaja_id`)
); ENGINE=InnoDB

CREATE TABLE `aiheet` (
	`aihe_id` int(11) unsigned NOT NULL AUTO_INCREMENT,
	`aihe` varchar(255) NOT NULL,
  `aika` DATETIME,
	`kayttaja_id` int(11) unsigned NOT NULL,
  PRIMARY KEY  (`aihe_id`),
	FOREIGN KEY (kayttaja_id)
		REFERENCES kayttajat(kayttaja_id)
		ON UPDATE CASCADE ON DELETE RESTRICT
); ENGINE=InnoDB

CREATE TABLE `viestit` (
	`viesti_id` int(11) unsigned NOT NULL AUTO_INCREMENT,
	`viesti` TEXT NOT NULL,
  `aika` DATETIME,
	`kayttaja_id` int(11) unsigned NOT NULL,
	`aihe_id` int(11) unsigned NOT NULL,
  PRIMARY KEY  (`viesti_id`),
	FOREIGN KEY (aihe_id)
		REFERENCES aiheeet(aihe_id)
		ON UPDATE CASCADE ON DELETE RESTRICT,
	FOREIGN KEY (kayttaja_id)
		REFERENCES kayttajat(kayttaja_id)
		ON UPDATE CASCADE ON DELETE RESTRICT
); ENGINE=InnoDB

/* Testi dataa, lisätään muutema käyttäjää */
INSERT INTO kayttajat (kayttaja_nimi) VALUES ('Useri1');
INSERT INTO kayttajat (kayttaja_nimi) VALUES ('Useri2');
INSERT INTO kayttajat (kayttaja_nimi) VALUES ('Useri3');

/* Lisätään userin yksi (jonka id pitäs olla nyt 1 tässä vaiheessa) tekemä aihe aiheisiin */
INSERT INTO aiheet (aihe, kayttaja_id, aika) VALUES ('Userin 1 tekemä aihe', 1, NOW());

/* Lisätään aiheeseen vastaukset userilta 2 ja 3 */
INSERT INTO viestit (viesti, aika, kayttaja_id, aihe_id) VALUES ('Eka viesti aiheeseen', NOW(), 2, 1);
INSERT INTO viestit (viesti, aika, kayttaja_id, aihe_id) VALUES ('Toka viesti aiheeseen', NOW(), 3, 1);

/* Alla olevalla kyselyllä haetaan aiheet ja niiden aloittajat uusimmasta vanhimpaan */
SELECT a.aihe, a.aika, k.kayttaja_nimi AS aloittaja
	FROM aiheet a
	LEFT JOIN kayttajat k ON k.kayttaja_id = a.kayttaja_id
	ORDER BY a.aika DESC

/* Alla olevalla kyselyllä haetaan johonkin aiheeseen
   liittyvät viestit ja niiden postaajien kayttaja nimet */
SELECT v.viesti, v.aika, k.kayttaja_nimi
	FROM viestit v
	LEFT JOIN aiheet a ON a.aihe_id = v.aihe_id
	LEFT JOIN kayttajat k ON k.kayttaja_id = v.kayttaja_id
	WHERE v.aihe_id = 1
	ORDER BY a.aika DESC

Triton [01.06.2009 20:23:59]

#

MIB kirjoitti:

Noin en saanut toimimaan. Miten kuuluu luoda siis taulukko, jossa on id ja otsikko?

Siis se taulu luodaan, vaikka näin:

CREATE TABLE aiheet (id int unsigned auto_increment not null primary key, otsikko varchar(100))

MIB [01.06.2009 20:32:12]

#

Triton kirjoitti:

Siis se taulu luodaan, vaikka näin:

CREATE TABLE aiheet (id int unsigned auto_increment not null primary key, otsikko varchar(100))

Kiitos! Näin tämä toimii mahtavasti. Nytten vähän lisään tuohon tavaraa, ja saan ID:n perusteella kaikki toimimaan. :) Sitten saan toimimaan muokkaus ja poisto koodit.

EDIT: Jostain kumman syystä tämä ei toimi:

mysql_query("CREATE TABLE viestit(aihe_id int unsigned auto_increment not null primary key,
viesti_id int unsigned auto_increment not null primary key,
otsikko varchar(100),
lähettäjä_id TEXT,
aika INT,
viesti varchat(100))");

Metabolix [01.06.2009 20:51:41]

#

Kannattaa ehkä lueskella niitä MySQL:n virheilmoituksia sekä omaa koodia.

MIB kirjoitti:

varchat

Myöskään primary keytä ei pidä käyttää kahdessa kohti, vaan aihe_id:n kuuluisi oikeammin olla foreign key, joka viittaa aihetauluun. (Laiskat jättävät foreign keyt kokonaan pois.) Lisäksi lähettäjän pitäisi olla INT ja viestin maksimipituuden luultavasti enemmän kuin 100 merkkiä. Ääkkösiäkään ei moni suosi tietokannoissa, voivat aiheuttaa ikäviä merkistöongelmia.

TeNDoLLA [01.06.2009 20:52:01]

#

On tuossa muitakin virheitä. Primary keytä voi olla yksi per taulu tietääkseni ja nyt yrität laittaa kahta primary keytä. Kahdesta kentästä yhdessä voi tehdä primary keyn kyllä mutta sen tekeminen ei tapahdu noin.

Lisäksi auto_increment voi olla vain yhdessä columnissa myös, joka taas pitää olla määritetty keyksi.

edit: Keele Metabolix koko ajan ehtii ennemmin :)

MIB [01.06.2009 20:56:48]

#

TeNDoLLA kirjoitti:

On tuossa muitakin virheitä. Primary keytä voi olla yksi per taulu tietääkseni ja nyt yrität laittaa kahta primary keytä. Kahdesta kentästä yhdessä voi tehdä primary keyn kyllä mutta sen tekeminen ei tapahdu noin.

Lisäksi auto_increment voi olla vain yhdessä columnissa myös.

No muttah, miten sitten teen tämän? :S Nyt meni mulla tosi korkealta yli.

TeNDoLLA [01.06.2009 20:59:51]

#

Muokattu suoraan tuosta sun versiosta

mysql_query("CREATE TABLE viestit(aihe_id INT UNSIGNED AUTO_INCREMENT NOT NULL PRIMARY KEY,
viesti_id INT UNSIGNED NOT NULL,
otsikko varchar(255),
lahettaja_id INT,
aika DATETIME,
viesti TEXT)");

Metabolix [01.06.2009 21:17:19]

#

Samalla aihe_id:llä yleensä tulee monta viestiä, joten oikea muoto aiheille ja viesteille olisi kuitenkin tämä:

CREATE TABLE aiheet(
  aihe_id INT UNSIGNED AUTO_INCREMENT NOT NULL PRIMARY KEY,
  otsikko VARCHAR(255)
);
CREATE TABLE viestit(
  viesti_id INT UNSIGNED AUTO_INCREMENT NOT NULL PRIMARY KEY,
  aihe_id INT UNSIGNED NOT NULL,
  lahettaja_id INT,
  aika DATETIME,
  viesti TEXT
);

MIB [01.06.2009 21:44:39]

#

Ennen toimi jotenkin, mutta nyt ei mene ollenkaan. Pitänee kirjoittaa nuo pari koodia ihan uudelleen :S

TeNDoLLA [01.06.2009 21:45:55]

#

Hieman offtopic, mutta ihmettelen miksihän täällä ei ole SQL:lle omaa syntaksi väritystä.

MIB [02.06.2009 08:53:02]

#

Nyt tulee seuraava error: "You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near ')' at line 7"

Koodi

<?php
$yhteys = mysql_connect("localhost", "root", "");
mysql_select_db("forum");

mysql_query("CREATE TABLE viestit(
  viesti_id INT UNSIGNED AUTO_INCREMENT NOT NULL PRIMARY KEY,
  aihe_id INT UNSIGNED NOT NULL,
  lahettaja_id TEXT,
  aika INT,
  viesti TEXT,
)") or die(mysql_error());
mysql_close($yhteys);
?>

trilog [02.06.2009 09:47:51]

#

Pilkku pois viimeisen kentän perästä.

MIB [02.06.2009 09:51:28]

#

Kiitos.

MIB [02.06.2009 13:58:38]

#

Hmm... Jotain vaikeuksia koodini kanssa. Ainoastaan yksi virhe enään, sitten toimii kaikki :) (Tulee vielä lisää toimintoja)
Virhe on se, että kun kirjoitan aihetta:

<?php include("yla.php");
$yhteys = mysql_connect("localhost", "root", "");
mysql_select_db("forum", $yhteys);
  /////////////////////////////////////////////////////////////////////////////////
 //////////Tässä ei saa tehdä mitään muutoksia kuin if -lauseen sisään! //////////
/////////////////////////////////////////////////////////////////////////////////

$viesti = $_POST["viesti"];
$aika = time();
$lahettaja = $user['tunnus'];
$otsikko = $_POST["otsikko"];

//BBcode functiot
  function bbcode_format($var) {
	$search = array(
		'/\[b\](.*?)\[\/b\]/is',
		'/\[i\](.*?)\[\/i\]/is',
		'/\[u\](.*?)\[\/u\]/is',
		'/\[url\](.*?)\[\/url\]/is',
		'/\[url\=(.*?)\](.*?)\[\/url\]/is'
		);

	$replace = array(
		'<strong>$1</strong>',
		'<em>$1</em>',
		'<u>$1</u>',
		'<a href="$1">$1</a>',
		'<a href="$1">$2</a>'
		);

	$var = preg_replace ($search, $replace, $var);

	return $var;
}
//Kutsutaan bbcodea
$viesti = bbcode_format($viesti);

if (!empty($viesti) && !empty($otsikko)) {
$kirjoita_aihe = "INSERT INTO aiheet (otsikko, lahettaja, aika) VALUES ('$otsikko', '$lahettaja', '$aika')";
$kirjoita_viesti = "INSERT INTO viestit(aihe_id, lahettaja_id, aika, viesti) VALUES ('$aiheid', '$lahettaja', '$time', '$viesti')";

mysql_query($kirjoita_aihe, $yhteys);
mysql_query($kirjoita_viesti, $yhteys);
}
mysql_close($yhteys);
header("Location: alue.php?aiheid=$aiheid");
?>

Niin, en ole keksinyt miten haen uusimman aiheen (mikä luodaan ennen viestiä) ID:n ja laitan sen $aiheid muuttujaan.

TeNDoLLA [02.06.2009 14:09:27]

#

<?php
$query = "SELECT aihe_id FROM aiheet ORDER BY aika DESC LIMIT 1";
$result = mysql_query($query);
$result = mysql_fetch_assoc($result);
$aiheId = $result['aihe_id'];
?>

ps. en testannut.

MIB [02.06.2009 14:25:01]

#

TeNDoLLA kirjoitti:

<?php
$query = "SELECT aihe_id FROM aiheet ORDER BY aika DESC LIMIT 1";
$result = mysql_query($query);
$result = mysql_fetch_assoc($result);
$aiheId = $result['aihe_id'];
?>

ps. en testannut.

"
Warning: mysql_fetch_assoc(): supplied argument is not a valid MySQL result resource in C:\xampplite\htdocs\foorumi\setid.php on line 7
"

FOR silmukalla saan tehtyä, joka nyt ei ole maailman viisain tapa.
Parempia tapoja voi ilmoittaa :)

tsuriga [02.06.2009 14:39:37]

#

Mikäli virheilmoitus vaatii suomennosta niin se sanoopi, notta "annettu argumentti ei ole kelvollinen MySQL-tulosresurssi", ts. mysql_query on epäonnistunut, mikä kyllä pitäisi löytyä tulostuneista virheilmoituksista tai logeista.

MIB [02.06.2009 14:42:18]

#

tsuriga kirjoitti:

Mikäli virheilmoitus vaatii suomennosta niin se sanoopi, notta "annettu argumentti ei ole kelvollinen MySQL-tulosresurssi", ts. mysql_query on epäonnistunut, mikä kyllä pitäisi löytyä tulostuneista virheilmoituksista tai logeista.

No, tuli nyt tehtyä FOR silmukalla:

<?php
$yhteys = mysql_connect("localhost", "root", "");
mysql_select_db("forum");

$query = "SELECT aihe_id FROM viestit ORDER BY aika DESC LIMIT 1";
$result = mysql_query($query);

for ($i = 0; $i < mysql_num_rows($result); $i++) {
$id = mysql_result($result, $i, "aihe_id");
}
echo $id;

mysql_close($yhteys);
?>

EDIT:
Eipäs toimikkaan näin. Huomasin äsken. Miten kannattaisi tehdä? :p

ajv [02.06.2009 15:11:07]

#

Kandee laittaa toi tulostus tonne silmukan sisään.

MIB [02.06.2009 15:27:14]

#

ajv kirjoitti:

Kandee laittaa toi tulostus tonne silmukan sisään.

Enpä tiedä, ei se toimi siltikään oikein.
Voisinkos tehdä sen jotenkin muuten? For silmukka ei ole ihan paras vaihtoehto mielestäni.

Metabolix [02.06.2009 15:32:14]

#

Annoin jo aiemmin tässä keskustelussa while-silmukan tulosten hakemiseen.

MIB [02.06.2009 15:44:47]

#

<?php
$y = mysql_connect("localhost", "root", "");
mysql_select_db("forum");

$kysely = "SELECT * FROM aiheet ORDER BY aika DESC";
$hae = mysql_query($kysely, $y) or die(mysql_error());
while ($rivi = mysql_fetch_assoc($hae)) {
  // Taulukossa ovat kätevästi kaikki hakutuloksen tiedot.
  $id = $rivi["aihe_id"];
  echo $id;
}
mysql_close($y);
?>

Ei tulosta mitään...

opt [02.06.2009 15:46:48]

#

Kyllä tähän ei mitään looppeja tarvita.

$kirjoita_aihe = "INSERT INTO aiheet (otsikko, lahettaja, aika) VALUES ('$otsikko', '$lahettaja', '$aika')";
mysql_query($kirjoita_aihe, $yhteys);

$aiheid = mysql_insert_id($yhteys);
$kirjoita_viesti = "INSERT INTO viestit(aihe_id, lahettaja_id, aika, viesti) VALUES ('$aiheid', '$lahettaja', '$time', '$viesti')";
mysql_query($kirjoita_viesti, $yhteys);

MIB [02.06.2009 16:04:36]

#

$aiheid = mysql_insert_id($yhteys);

Mitä tämä perjaatteessa tekee? Minusta tuo ei hae tuota tietoa sitten mistään.

EDIT: Hups, mun moka.. Toi Metabolixin juttu toimi hyvin, mutta hain väärän nimistä id:tä.

opt [02.06.2009 16:07:18]

#

Retrieves the ID generated for an AUTO_INCREMENT column by the previous INSERT query.

Hakee siis edellisen insertin auto_increment kolumnin arvon.

MIB [02.06.2009 16:08:57]

#

opt kirjoitti:

Retrieves the ID generated for an AUTO_INCREMENT column by the previous INSERT query.

Hakee siis edellisen insertin auto_increment kolumnin arvon.

Sittenhän tämäkin on kätevä.

TeNDoLLA [02.06.2009 18:54:49]

#

On se kätevä niin kauan kun olet viimeksi INSERTannu nimenomaan siihen aihe tauluun, mutta jos inserttaatkin välissä johonkin muuhun tauluun, jossa on ID myös niin se hakeekin sieltä sen viimeisimmän ID:n eikä aiheista. Tuo mun laittama ratkaisu oli tarkotettu toimivaksi näin yleisellä tasolla riippumatta edellisestä kyselystä. Tosin sun tapauksessa se edellinen kysely nyt sattuu juuri olemaan se aiheet taulun insertti.

Ja kyllä tämä toimii täysin. Mulle ainakin tulee se uusin aihe_id tuonne $aiheId muuttujan ja nyt testasinkin tämän.

<?php
$query = "SELECT aihe_id FROM aiheet ORDER BY aika DESC LIMIT 1";
$result = mysql_query($query);
$result = mysql_fetch_assoc($result);
$aiheId = $result['aihe_id'];
echo $aiheId // Echo lisätty edelliseen esimerkkiin vain..
?>

Edit1: Ilmeisesti sulla ei se mysql_query toiminut tuossa, koska ei palauttanut oikeata mysql resurssia ? Eli jos copy&pastesit suoraan tuon sinne, niin ootko varma, että sulla on taulun nimet kannassa se 'aiheet' sekä kentän nimet 'aihe_id' ja 'aika' täsmälleen eikä melkein mitä käytät tuossa kyselyssä? Ootko avannut ennen tuota mysql yhteyden mysql_connectilla ja valinnat myös kannan mysql_select_db:llä?

Grez [02.06.2009 19:06:55]

#

MIB sanoi kaksi keskenään ristiriitaista tarvetta:

"Niin, en ole keksinyt miten haen uusimman aiheen (mikä luodaan ennen viestiä) ID:n ja laitan sen $aiheid muuttujaan."

Eli tarpeet olivat:
1) Uusimman aiheen Id:n hakeminen
2) Sen aiheen Id:n hakeminen, joka juuri luotiin

TeNDoLLA:n ratkaisu toteuttaa kohdan 1.

Sen sijaan kun MIB haluaa luoda aiheen ja siihen aiheeseen liittyvän viestin, niin hän tarvitsee vaihtoehdon 2, eli insert_id on oikea vaihtoehto.

TeNDoLLA [02.06.2009 19:08:18]

#

Se on totta juu. Ajattelin vain vielä varmistaa, että meni perille miten se toimii, koska on tuntunut tässä threadin edetessä että OP on aika pihalla.

edit: tosin nyt kun kattoo niin ihan turhaa motkotusta.. kyllähän se lukee selvällä englannin kielelläkin jo tuossa aiemmin :)

ps. vasta herännyt...

ps2. OT: Grez ollut kesälomilla kun ei ole vastaillut aikoihin?

MIB [02.06.2009 20:22:21]

#

Miten tämä lainaus juttu kannattaa tehdä? Tein niin, että koodi tekee BBcoden (Tämä toimii, ja lainaus linkistä tulee sisältö kyllä lainaus tagien väliin)

[lainaus "Keneltä"]Viesti käyttäjältä[/lainaus]

Mutta, en osaa korvata näitä HTML merkinnällä.

Muut BBcode tagit teen näin:

function bbcode_format($var) {
	$search = array(
		'/\[b\](.*?)\[\/b\]/is',
		'/\[i\](.*?)\[\/i\]/is',
		'/\[u\](.*?)\[\/u\]/is',
		'/\[url\](.*?)\[\/url\]/is',
		'/\[url\=(.*?)\](.*?)\[\/url\]/is',
		);

	$replace = array(
		'<strong>$1</strong>',
		'<em>$1</em>',
		'<u>$1</u>',
		'<a href="$1">$1</a>',
		'<a href="$1">$2</a>',
		);

	$var = preg_replace ($search, $replace, $var);

	return $var;
}

trilog [02.06.2009 20:50:40]

#

MIB kirjoitti:

Miten tämä lainaus juttu kannattaa tehdä? Tein niin, että koodi tekee BBcoden (Tämä toimii, ja lainaus linkistä tulee sisältö kyllä lainaus tagien väliin)

[lainaus "Keneltä"]Viesti käyttäjältä[/lainaus]

Mutta, en osaa korvata näitä HTML merkinnällä.

Kopioitu suoraan Ohjelmointiputkan lähdekoodista lisättynä tuohon BB-code -funktioon:

<?php
function bbcode_format($var) {
	$search = array(
		'/\[b\](.*?)\[\/b\]/is',
		'/\[i\](.*?)\[\/i\]/is',
		'/\[u\](.*?)\[\/u\]/is',
		'/\[url\](.*?)\[\/url\]/is',
		'/\[url\=(.*?)\](.*?)\[\/url\]/is',
		'/\[lainaus "(.*?)"\](.*?)\[\/lainaus\]/is',
		);

	$replace = array(
		'<strong>$1</strong>',
		'<em>$1</em>',
		'<u>$1</u>',
		'<a href="$1">$1</a>',
		'<a href="$1">$2</a>',
		'<i><small>$1 kirjoitti:</small></i><br><div style="border-style:solid;border-width:1px;background:#E4E9FF;margin-left:8px">$2</div>',
		);

	$var = preg_replace ($search, $replace, $var);

	return $var;
}
?>

MIB [02.06.2009 21:32:45]

#

Kun kiellän viesteissä HTML merkinnät, niin miten voin sallia, että lainauksissa kaikki on sallittu?

Teuro [02.06.2009 21:38:13]

#

Miksi ne pitäisi lainauksissa sallia? Eihän viestin rakennetta muuteta, kuin tulostuksen aikana.

MIB [02.06.2009 21:41:43]

#

Teuro kirjoitti:

MIB kirjoitti:

Kun kiellän viesteissä HTML merkinnät, niin miten voin sallia, että lainauksissa kaikki on sallittu?

Miksi ne pitäisi lainauksissa sallia?

Koska, jostain syystä esimerkiksi viesti

Moi

Mitä kuuluu?

tulostuu

käyttäjä kirjoitti:

Moi
<br>
<br>Mitä kuuluu?

ja jos siinä on muita BBcode tageja, niin ne tulostuvat myös <b>, <a href=""></a> jne.

Kun tuon saa toimimaan, niin olisi kiva olla myös sellainen, että viestiä ei muuteta HTML muotoon ennen kirjoitusta vaan sen tulostuksen aikana tai kun vastaus lainataan, niin siinä ei lukisi suoraan <a href=""></a> tai mitään muuta, vaan se BBcode tagi.

Sen takia pitäisi sallia HTML, kun BBcode tagit ovat HTML muodossa kannassa.

Teuro [02.06.2009 21:44:51]

#

Eikö lainaus kannata hakea tietokannasta, jossa lainattu viesti on tietenkin ilman muunnettuja bb-codeja eikös vain?

MIB [02.06.2009 21:47:38]

#

Teuro kirjoitti:

Eikö lainaus kannata hakea tietokannasta, jossa lainattu viesti on tietenkin ilman muunnettuja bb-codeja eikös vain?

Sitähän tuossa viestissäni mainitsin, mutta miten tulostaessa ne korvataan sitten? Kun tulostan viestin tietyssä kohtaa muuttujassa $viesti, niin laitanko ennen tulostusta tuon minun BBcode muunto jutun? (Minkä trilog postasi tuohon)

Teuro [02.06.2009 21:50:30]

#

Erillisellä muunosfunktiolla kannattaa lähteä liikkeelle. Tällä tavalla saat muutettua tarvottaessa hyvinkin helposti viestien ulkoasuakin.

MIB [02.06.2009 21:51:00]

#

Teuro kirjoitti:

Erillisellä muunosfunktiolla kannattaa lähteä liikkeelle. Tällä tavalla saat muutettua tarvottaessa hyvinkin helposti viestien ulkoasuakin.

Okei, mutta tämä yllämainitsemani tapa toimii?

MIB [03.06.2009 08:29:02]

#

Joo, kyllä sain toimimaan nyt ;)

MIB [03.06.2009 10:43:59]

#

Hitsi kun menee toi muokkaus aika umpeen näin nopeesti. Mutta niin.
Tuo trilogin BBcode juttu toimii hyvin, mutta se ei osaa sellaista asiaa, kuin kaiksi lainausta sisäkkäin. Kahdella lainauksella sisäkkäin käy näin:

Linkki virhekuvaan

Miten korjaisin?

TeNDoLLA [03.06.2009 11:20:56]

#

Googlella löyty samoja ongelmia jollain muillakin, löysin jonkun pätkän jota muokkasin vähän. Takuuseen en mene miten tää toimii esim. auki jätettyjen tagien kanssa, mutta toimi ainakin tuossa sun esimerkissäs.

<?php
function bbcode_format($var) {
    $search = array(
        '/\[b\](.*?)\[\/b\]/is',
        '/\[i\](.*?)\[\/i\]/is',
        '/\[u\](.*?)\[\/u\]/is',
        '/\[url\](.*?)\[\/url\]/is',
        '/\[url\=(.*?)\](.*?)\[\/url\]/is',
        '/\[lainaus\](.*?)/is',
        '/\[lainaus "(.*?)"\](.*?)/is',
        '/\[\/lainaus\]/is',
        );

    $replace = array(
        '<strong>$1</strong>',
        '<em>$1</em>',
        '<u>$1</u>',
        '<a href="$1">$1</a>',
        '<a href="$1">$2</a>',
        '<div style="background:#F8F8F8;border:1px solid #E4E4E4;">$1',
        '<div style="background:#F8F8F8;border:1px solid #E4E4E4;"><b>by$1</b><br/>$2',
        '</div>',
        );
    $var = preg_replace ($search, $replace, $var);
    return $var;
}
?>

Edit: Eli eronahan tuossa on vain se, että lainauksen avaus ja lukitus tagit käsitellään erikseen sen sijaan, että käsittelet tuossa aikaisemmin samassa molemmat.

MIB [03.06.2009 11:23:59]

#

Toi ainakin toimii, mutta menee hetki muokata oikeen näkönen. :S

EDIT: Voiko lähettää POSTIlla tavaraa ilman lomaketta?

MIB [03.06.2009 13:16:26]

#

Ärsyttää, kun menee näin nopeesti lukkoon toi editointi... :S

Niin, yks juttu viellä.
Jos haluan siinä järjestyksessä aiheet, kun niihin viimeinen viesti on lähetetty, niin mitä kuuluisi lisätä?
SELECT * FROM aiheet ORDER BY _______________

Ajattelin, että se katsoo, että mikä on uusimman viestin aika, sitten katsoo aihe_id:n ja sitten laittaa oikeaan järjestykseen. En vaan tiedä miten kuuluu tarkistaa, tai oikeastaan miten se kysely menisi.

Teuro [03.06.2009 13:29:43]

#

Saat sen helpoimmalla ehkä, kun teet kyselyn, jossa ryhmittelet viestit aihei_id:n perusteella ryhmiksi. Lopuksi järjestelet kyselyn lähetysajan mukaan laskevaan järjestykseen.

MIB [03.06.2009 13:32:45]

#

Teuro kirjoitti:

Saat sen helpoimmalla ehkä, kun teet kyselyn, jossa ryhmittelet viestit aihei_id:n perusteella ryhmiksi. Lopuksi järjestelet kyselyn lähetysajan mukaan laskevaan järjestykseen.

Kuten sanoin, nuo SQL lauseet ovat hakusessa.

Ryhmittelen? Siis, GROUP BY?

Teuro [03.06.2009 13:41:57]

#

MIB kirjoitti:

Kuten sanoin, nuo SQL lauseet ovat hakusessa.

Tekemällä oppii ja siperia opettaa.

MIB kirjoitti:

Ryhmittelen? Siis, GROUP BY?

Kyllä.

<?php
$kysely = "
SELECT
  aihe_id,
  DATE_FORMAT(MAX(lahettetty), '%e.%c.%Y') AS aika,
  otsikko
FROM
  viestit
GROUP BY
  aihe_id
ORDER BY
  aika DESC";

$tulokset = mysql_query($kysely);

/* Tulostaminen */
while($rivi = mysql_fetch_array($tulokset)){
  echo $rivi['aika'] . " " . $rivi['otsikko'] . "<br />";
}

MIB [03.06.2009 13:51:29]

#

DATE_FORMAT?
Tarkoittaako tämä sitä, että aika olisi DATEna tuolla tietokannassa?
En saanut toimimaan

Warning: mysql_fetch_array(): supplied argument is not a valid MySQL result resource in C:\xampplite\htdocs\foorumi\groupby.php on line 20

:S

Teuro [03.06.2009 13:58:34]

#

MIB kirjoitti:

DATE_FORMAT? Tarkoittaako tämä sitä, että aika olisi DATEna tuolla tietokannassa? En saanut toimimaan

Kyllä kai päivämäärät kannattaa pitää ihan timestamppina kannassa, jolloin tuo DATE_FORMAT(time, format) funktio osaa käsitellä tuota oikein. Millainen virhe mysql_error() funktion mukaan tuolla on? Monasti se osaa kertoa aika tarkkaan virheestä. Selvää lienee kuitenkin, että ainakin osa kenttien nimistä lienee väärin.

TeNDoLLA [03.06.2009 14:04:32]

#

Jos en ihan väärin muista, niin taitaa olla INT tyyppisinä MIBillä nuo aika kentät, joten eikös se silloin toimis muuten samaan tyyliin, mutta ilman tuota DATE_FORMATia.

MIB [03.06.2009 14:13:59]

#

TeNDoLLA kirjoitti:

Jos en ihan väärin muista, niin taitaa olla INT tyyppisinä MIBillä nuo aika kentät, joten eikös se silloin toimis muuten samaan tyyliin, mutta ilman tuota DATE_FORMATia.

INTnä on joo, katon jos saan tuon toimimaan.

<?php
$y = mysql_connect("localhost", "root", "");
mysql_select_db("forum");

$kysely = "
SELECT
  id,
  aika,
  otsikko
FROM
  aiheet
GROUP BY
  id
ORDER BY
  aika DESC";

$tulokset = mysql_query($kysely) or die(mysql_error());

/* Tulostaminen */
while($rivi = mysql_fetch_array($tulokset)){
  echo $rivi['aika'] . " " . $rivi['otsikko'] . "<br />";
}
mysql_close($y);
?>

Tuo toimii melkein, mutta ei katso uusinta viestiä vielä, vaan uusimman aiheen. :D Muunnan vähän niin toimii.

MIB [03.06.2009 15:21:23]

#

Ei onnistu.
Aiheet taulu on tämmöinen:
id
otsikko
aika
viesti

Ja viestit taulu
viesti_id
aihe_id
lahettaja
aika
viesti

Joten, miten katson uusimman ajan viesteistä, ja järjestelen siten tuon aihe listan. (Ei aiheet taulua, vaan lista sivulla)
En saa tehtyä tuolla esimerkilläsi, kun viesteissä ei ole otsikkoa.

Grez [03.06.2009 16:34:27]

#

Suunnilleen tälleen (en testannut, mutta idea selvinnee vaikkei ihan toimisikaan)

SELECT
  a.id,
  a.otsikko,
  Max(v.aika) ViimeisinViesti
FROM
  Aiheet a
  JOIN viestit v ON (v.aihe_id=a.id)
GROUP BY
  a.id,
  a.otsikko
ORDER BY
  Max(v.aika) DESC

MIB [03.06.2009 16:40:41]

#

Grez kirjoitti:

Suunnilleen tälleen (en testannut, mutta idea selvinnee vaikkei ihan toimisikaan)

SELECT
  a.id,
  a.otsikko,
  Max(v.aika) ViimeisinViesti
FROM
  Aiheet a
  JOIN viestit v ON (v.aihe_id=a.id)
GROUP BY
  a.id,
  a.otsikko
ORDER BY
  Max(v.aika) DESC

Muutama kysymys:
1. Mitä nuo a ja v kirjaimet vaikuttavat tuolla?
2. Mikä tuo ViimeisinViesti juttu on, tai oikeastaan mitä siihen kuuluu laittaa? En usko että tekee mitään noin?

kayttaja-2791 [03.06.2009 16:43:24]

#

MIB kirjoitti:

Muutama kysymys:
1. Mitä nuo a ja v kirjaimet vaikuttavat tuolla?
2. Mikä tuo ViimeisinViesti juttu on, tai oikeastaan mitä siihen kuuluu laittaa? En usko että tekee mitään noin?

Kumpaankin vastaus on että ne ovat aliaksia. Ensin annetaan tuolle Max-arvolle nimeksi ViimeisinViesti, ja taulut nimetään a:ksi ja v:ksi. Nimeäminen vaikuttaa sitten itse kyselyyn, sekä palautettaviin tuloksiin.

MIB [03.06.2009 16:45:27]

#

JTS kirjoitti:

MIB kirjoitti:

Muutama kysymys:
1. Mitä nuo a ja v kirjaimet vaikuttavat tuolla?
2. Mikä tuo ViimeisinViesti juttu on, tai oikeastaan mitä siihen kuuluu laittaa? En usko että tekee mitään noin?

Kumpaankin vastaus on että ne ovat aliaksia. Ensin annetaan tuolle Max-arvolle nimeksi ViimeisinViesti, ja taulut nimetään a:ksi ja v:ksi. Nimeäminen vaikuttaa sitten itse kyselyyn, sekä palautettaviin tuloksiin.

Okei.

KIITOS GREZ! Tuo toimii ilman mitään muokkausta tuonne koodiin :)

MIB [03.06.2009 18:48:42]

#

Muokkasin niin, että toimii minulla oikeassa kohtaa:

SELECT
  a.id,
  a.otsikko,
  a.lahettaja,
  v.aika,
  Max(v.aika) ViimeisinViesti
FROM
  Aiheet a
  JOIN viestit v ON (v.aihe_id=a.id)
GROUP BY
  a.id,
  a.otsikko
ORDER BY
  Max(v.aika) DESC

Nyt vain on seuraavan lainen ongelma. Kun haluaisin, että järjestyksen lisäksi olisi "Viimeinen viesti" kohta taulukossa, niin miten kannattaisi toteuttaa?

***keskustelu.php
<?php
require_once("settings.php");
$yhteys = mysql_connect("$dbserver", "$dbuser", "$dbpw") or die(mysql_error());
mysql_select_db("$db", $yhteys) or die(mysql_error());

$kysely = "SELECT
  a.id,
  a.otsikko,
  a.lahettaja,
  v.aika,
  Max(v.aika) ViimeisinViesti
FROM
  Aiheet a
  JOIN viestit v ON (v.aihe_id=a.id)
GROUP BY
  a.id,
  a.otsikko
ORDER BY
  Max(v.aika) DESC";
$haku = mysql_query($kysely, $yhteys) or die(mysql_error());

echo '<table class="teksti" width="95%" cellspacing="0">';
echo '<tr class="taulukkoyla">
<td width="50%"><b>Aiheen otsikko</b></td>
<td width="30%"><b>Aloittaja</b></td>
<td><b>Aloitusaika</b></td></tr>';

//Käydään kaikki aiheet läpi, ja laitetaan tiedot muuttujiin.
for ($i = 0; $i < mysql_num_rows($haku); $i++) {
   $aihe_id = mysql_result($haku, $i, "id");
   $aloittaja = mysql_result($haku, $i, "lahettaja");
   $aika = mysql_result($haku, $i, "aika");
   $otsikko = mysql_result($haku, $i, "otsikko");

   //Siistitään aika
   $siistittyaika = date("d.m.y H:i:s", $aika);
   //Tulostetaan aiheet.
   echo "<tr><td><a href=\"alue.php?aiheid=$aihe_id\">$otsikko</a></td><td><a href=\"profiili.php?tunnus=$aloittaja\">$aloittaja</a></td><td>$siistittyaika</td></tr>";
}
echo "</table><br><hr>";

echo '<div style="padding-left: 15px">';
if($user) {
?>
<form action="uusiaihe.php" method="post">
<b>Otsikko:</b><br><input type="name" name="otsikko">
<br><br><b>Viesti:</b><br><textarea name="viesti" cols="80" rows="15"></textarea><br><br>
<input type="submit" value="Luo aihe">
</form>
<?php }
else echo "Sinun pitää kirjatua sisään aloittaaksesi aiheen!";
?>
</div>

Tuossa nyt vielä se koodi mihin tuo järjestys kysely tulee.
Tietokantojen (aiheet & viestit) rakenteet laitoinkin jo tuossa aikaisemmin.
Ajattelin tehdä uuden kyselyn, jossa ryhmittelen aihe_id:n perusteella viestit, ja tulostan aina oikean aiheen kohdalla viimeisimmän viestin lähettäjän ja ajan, milloin on postannut viestin. Toteutus vain uupuu.

Grez [03.06.2009 19:19:11]

#

Toki tuossa on montakin tapaa. Itse hyödyntäisin varmaan sitä seikkaa, että viestit ovat myös Id:n puolesta aikajärjestyksessä.

MIB [03.06.2009 19:25:57]

#

En saa millään tuota tehtyä. Vaikea juttu. :S

EDIT: Onnistuisiko näin?

SELECT aika, lahettaja_id, aihe_id FROM viestit GROUP BY aihe_id ORDER BY aika DESC LIMIT 1

Sitten vaan hoidetaan muut tulostukset.

Grez [03.06.2009 19:48:31]

#

Itse ajattelin että teen viewn ja sitten käytän sitä kyselyssä, mutta MySQL:ssä testaaminen kaatuu siihen että mulla ei näköjään ole Create View oikeutta palveluntarjoajan MySQL:ssä enkä nyt jaksa asentaa omalle koneelle.

Anyways, jotain tällaista ajattelin:

CREATE VIEW AiheetViimeisinViesti AS
SELECT
  a.id,
  a.otsikko,
  Max(v.viesti_id) viesti_id
FROM
  Aiheet a
  JOIN viestit v ON (v.aihe_id=a.id)
GROUP BY
  a.id,
  a.otsikko

ja sitten itse kysely

SELECT
  a.id,
  a.otsikko,
  v.lahettaja,
  v.aika,
  v.viesti
FROM
  AiheetViimeisinViesti a LEFT JOIN
  viestit v ON a.viesti_id=v.viesti_id
ORDER BY
  a.id

MIB [03.06.2009 19:58:52]

#

En kyllä haluaisi kirjoittaa aiheet taulua uudelleen, kun muitakin tapoja on toteuttaa tämä.

<?php
$y = mysql_connect("localhost", "root", "");
mysql_select_db("forum");

$kysely = "
SELECT
 aika,
 lahettaja_id,
 aihe_id,
 viesti,
 viesti_id
FROM
 viestit
GROUP BY
 viesti_id
ORDER BY
 viesti_id DESC
LIMIT 1";
$haku = mysql_query($kysely) or die(mysql_error());

while($rivi = mysql_fetch_array($haku)){
echo '<table class="teksti" width="100%" cellspacing="0">';
echo '<tr>
<td bgcolor="#464b4e"><font color="white"><b>Keskustelu:</b></font></td></tr></table>';
$aika = date("d.m.Y H:i:s", $rivi['aika']);
  echo "".$rivi["viesti"]."<br />(<a href=\"alue.php?aiheid=".$rivi['aihe_id']."\">Lue lisää...</a>)";
}

mysql_close($y);
?>

Tämän näköisen systeemin sain tehtyä. Koodi näyttää uusimman viestin foorumilla, ja laittaa siihen linkin.
Mutta, tämä ei liity siihen mitä hain. Tuli vaan tehtyä tämä, kun koitin sitä toista... :D

tsuriga [03.06.2009 21:51:14]

#

Asian vierestä, mutta sopivasti sivuten:

Kannattaa jo heti suorilta käsin kirjoittaa mieluummin tuon or die:n tilalle

Olioilla/PHP5:

<?php

/*
 * Esimerkeissä $queryError on / voi olla nimensä
 * mukaisesti tietokannan palauttama virheviesti.
 * Esim. vaikkapa se funktion mysql_error()-
 * funktion palauttama arvo.
 */

if ($result === false) {
    throw new Exception($queryError);
}

?>

Proseduurinen/PHP4 tapa:

<?php
if ($result === false) {
    trigger_error($queryError, E_USER_ERROR);
}

?>

Näin koodia ei tarvitse muokata enää sitten erikseen tuotantokäyttöön. Toki tuohon kannattaa jokin poikkeus-/virheenkäsittelijä tehdä (ks. set_exception_handler/set_error_handler), jotta käyttäjille saadaan tulostettua jokin selkokielinen virheilmoitus virhetilanteissa. Virheet eivät tulostu suoraan käyttäjille, vaikka poikkeus-/virheenkäsittelijä unohtuisikin (olettaen, että tuotantoserveri on konffittu oikein, eli virheitä ei suoraan puupata sivulle, vaan logiin).

Muistaakseni PHP:n oma manuaali suosittelee poikkeuksien käyttämistä errorien sijaan aina vitosversiosta lähtien.

MIB [04.06.2009 08:06:02]

#

Voisihan noinkin sen olioilla tehdä, mutta nyt kismittää liikaa tuo pääasia. :/
Sen varmaan saan tehtyä pian, mutta tuo koodi minkä laitoin tuohon. Jos viesti on esimerkiksi yli 250 merkkiä, niin 250 ensimmäistä merkkiä näytetään ja lopun tilalle tulee ... Koitin varcharia, mutta sitä käytetään vaan kirjoittaessa nähtävästi.

Teuro [04.06.2009 09:03:00]

#

Eikös sen saa ihan SUBSTRING(viesti, alku, pituus) funktiolla? Kannattaa lueskella tuota manuaalia, sieltä löytyy aika paljon tietoa. Sivu on tosin englanniksi, mutta se tuskin haittaa?

MIB [06.06.2009 12:19:19]

#

Teuro kirjoitti:

Eikös sen saa ihan SUBSTRING(viesti, alku, pituus) funktiolla? Kannattaa lueskella tuota manuaalia, sieltä löytyy aika paljon tietoa. Sivu on tosin englanniksi, mutta se tuskin haittaa?

En saanut näin toimimaan.
Mutta, jos laitan näin? SELECT SUBSTRING(viesti, 0, 200);. Toimisiko? En voi kokeilla, kun en pääse juuri nyt käsiksi serveriin.

Metabolix [06.06.2009 12:24:46]

#

SQL:ssä tekstin indeksit alkavat ykkösestä, mutta muuten meni oikein. Tietenkin tarvitset myös taulut ja ehdot kyselyyn.

SELECT
  viesti_id,
  SUBSTRING(viesti, 1, 100) AS alku,
  aihe_id
FROM viestit
ORDER BY viesti_id DESC
LIMIT 1

MIB [06.06.2009 12:29:00]

#

Metabolix kirjoitti:

SQL:ssä tekstin indeksit alkavat ykkösestä, mutta muuten meni oikein. Tietenkin tarvitset myös taulut ja ehdot kyselyyn.

SELECT
  viesti_id,
  SUBSTRING(viesti, 1, 100) AS alku,
  aihe_id
FROM viestit
ORDER BY viesti_id DESC
LIMIT 1

No joo, tietenkin tarvitsen nuo muut ehdot ja taulut, mutta toi oli suoraan Copy paste tekniikalla otettu manuaalista.
Kiitos sinulle!

MIB [06.06.2009 17:26:57]

#

Kun noita BBcode -tageja foorumille lisäilin, niin haluaisin laittaa PHP koodille värityksen. Higlight-string värittää, sen itsekkin tiesin.
Mutta, sitten kun luon kooditagit, niin miten väritän niiden sisällön?

<?php
function bbcode_format($var) {
    $search = array(
        '/\[b\](.*?)\[\/b\]/is',
        '/\[i\](.*?)\[\/i\]/is',
        '/\[u\](.*?)\[\/u\]/is',
        '/\[url\](.*?)\[\/url\]/is',
        '/\[url\=(.*?)\](.*?)\[\/url\]/is',
        '/\[lainaus\](.*?)/is',
        '/\[lainaus "(.*?)"\](.*?)/is',
        '/\[\/lainaus\]/is',
        );

    $replace = array(
        '<strong>$1</strong>',
        '<em>$1</em>',
        '<u>$1</u>',
        '<a href="$1">$1</a>',
        '<a href="$1">$2</a>',
        '<i><small>$1 kirjoitti:</small></i><br><div style="border-style:solid;border-width:1px;background:#E4E9FF;margin-left:8px">$2<br></div>',
        '<i><small><br>$1 kirjoitti:</small></i><br><div style="border-style:solid;border-width:1px;background:#E4E9FF;margin-left:8px">$2',
        '<br></div>',
        );
    $var = preg_replace ($search, $replace, $var);
    return $var;
}
?>

BBcode -koodi on nyt tälläinen.
Eli, kooditagien sisällä olisi väritys PHP koodille.

Tumettaja [06.06.2009 17:33:07]

#

Suosittelen käyttämään GeSHi syntaksi värittäjää joka on tarkoitettu PHP:n kanssa käytettäväksi. Näin säästyt
siltä työltä että tarvitset tehdä jokaiselle eri kielelle oman BBcode tagin.

MIB [06.06.2009 17:40:46]

#

Tumettaja kirjoitti:

Näin säästyt
siltä työltä että tarvitset tehdä jokaiselle eri kielelle oman BBcode tagin.

Se tässä olisi tarkoitus - tehdä itse. Oppii samalla kun tekee, ja kun teen foorumia, niin haluaisin sen olevan kokonaan omaa käsialaa. ;)

Grez [06.06.2009 17:56:14]

#

Jos kerran haluat itse tehdä, niin koskiko kysymys sitä, että miten HTML:llä vaihdetaan tekstin väriä, vai?

Jos taas haluat tietää miten se "kannattaa" tehdä, niin hae se GeSHi, käy koodi läpi sisäistäen mitä siinä tehdään ja sitten koodaat sen itse.

MIB [06.06.2009 18:03:38]

#

Jos tekisi näin: Tekee ensin sen laatikon mihin koodi tulee. Sen jälkeen ottaa sen sisällön niistä koodi tageista ($1) ja laittaa sen muuttujaan esimerkiksi $varita, ja sitten echo higlight_string($varita);?

Grez [06.06.2009 18:08:35]

#

En näe miksei se toimisi, mutta luulin että haluat opetella tekemään sen "itse".

MIB [06.06.2009 18:09:23]

#

Grez kirjoitti:

En näe miksei se toimisi, mutta luulin että haluat opetella tekemään sen "itse".

Siis, en sitä väritys puolta, mutta en halua suoraan jotain valmis scriptiä.

EDIT: Miten otan muuttujaan sisällön? $varita = $1; tulostaa Parse error: parse error, expecting `T_VARIABLE' or `'$'' in C:\xampplite\htdocs\foorumi\bbcode.php on line, koska tuohan on numero...

trilog [06.06.2009 21:53:35]

#

MIB kirjoitti:

EDIT: Miten otan muuttujaan sisällön? $varita = $1; tulostaa Parse error: parse error, expecting `T_VARIABLE' or `'$'' in C:\xampplite\htdocs\foorumi\bbcode.php on line, koska tuohan on numero...

<?php
$varita = ${1};
?>

Andu [06.06.2009 22:29:40]

#

Kaikki säännölliseen lausekkeeseen sopivat merkkijonot saa preg_match_all-funktiolla.

MIB [06.06.2009 22:44:43]

#

Ei toimi, tulostaa 1. Vaikea juttu :s

Andu [06.06.2009 22:52:19]

#

Toimiipa hyvinkin jos käytät sitä oikein.

<?php
$maara = preg_match_all($pattern, $subject, $matches);
print_r($matches);
?>

MIB [07.06.2009 11:05:03]

#

Tarkoitin, että tuolla trilogin tavalla tulostuu vain 1 oikean sisällön sijaan.
Tuota sinun tapaa, Andu, en tajunnut mitä ajat takaa tuolla. :/
Koitin ottaa $1 muuttujaan ($varitatama = ${1};) ja värittää sen sitten Highlight_stringillä ($varitetty = highlight_string($varitatama);) ja laittaa tämän $varitetty muuttujan oikeaan paikkaan, mutta tulostaa sivun alkuun ensin 2x $1 ja sen jälkeen koodi laatikkoon 1.

trilog [07.06.2009 11:30:41]

#

Laita koodia näytille, miten olet sitä yrittänyt toteuttaa.

MIB [07.06.2009 11:35:45]

#

<?php
$varita = ${1};
$varitatama = highlight_string("$varita");
function bbcode_format($var) {
    $search = array(
        '/\[b\](.*?)\[\/b\]/is',
        '/\[i\](.*?)\[\/i\]/is',
        '/\[u\](.*?)\[\/u\]/is',
        '/\[url\](.*?)\[\/url\]/is',
        '/\[url\=(.*?)\](.*?)\[\/url\]/is',
        '/\[lainaus\](.*?)/is',
        '/\[lainaus "(.*?)"\](.*?)/is',
        '/\[\/lainaus\]/is',
		'/\[koodi\](.*?)\[\/koodi\]/is'
        );
    $replace = array(
        '<strong>$1</strong>',
        '<em>$1</em>',
        '<u>$1</u>',
        '<a href="$1">$1</a>',
        '<a href="$1">$2</a>',
        '<i><small>$1 kirjoitti:</small></i><br><div style="border-style:solid;border-width:1px;background:#E4E9FF;margin-left:8px">$2<br></div>',
        '<i><small><br>$1 kirjoitti:</small></i><br><div style="border-style:solid;border-width:1px;background:#E4E9FF;margin-left:8px">$2',
        '<br></div>',
		'<div style="border-style:solid;border-width:1px;background:white">'.$varitatama.'</div>'
        );
    $var = preg_replace ($search, $replace, $var);
    return $var;
}
?>

Ja näin myös

<?php
function bbcode_format($var) {
    $search = array(
        '/\[b\](.*?)\[\/b\]/is',
        '/\[i\](.*?)\[\/i\]/is',
        '/\[u\](.*?)\[\/u\]/is',
        '/\[url\](.*?)\[\/url\]/is',
        '/\[url\=(.*?)\](.*?)\[\/url\]/is',
        '/\[lainaus\](.*?)/is',
        '/\[lainaus "(.*?)"\](.*?)/is',
        '/\[\/lainaus\]/is',
		'/\[koodi\](.*?)\[\/koodi\]/is'
        );
    $replace = array(
        '<strong>$1</strong>',
        '<em>$1</em>',
        '<u>$1</u>',
        '<a href="$1">$1</a>',
        '<a href="$1">$2</a>',
        '<i><small>$1 kirjoitti:</small></i><br><div style="border-style:solid;border-width:1px;background:#E4E9FF;margin-left:8px">$2<br></div>',
        '<i><small><br>$1 kirjoitti:</small></i><br><div style="border-style:solid;border-width:1px;background:#E4E9FF;margin-left:8px">$2',
        '<br></div>',
		'<div style="border-style:solid;border-width:1px;background:white">'.highlight_string(${1}).'</div>'
        );
    $var = preg_replace ($search, $replace, $var);
    return $var;
}
?>

trilog [07.06.2009 12:05:06]

#

Jälkimmäinen on lähempänä oikeaa, oli kyllä kieltämättä aika kinkkinen juttu, mutta sain onnistumaan. Löysin putkan oppaasta, että PHP:n preg_replaceen voi antaa funktioita, jonka läpi korvattava teksti ajetaan. Antaa koodin puhua puolestaan:

<?php
function varitaPHP($s) {
    return '<div style="border-style:solid;border-width:1px;background:white">'.
           highlight_string($s, True).
           '</div>';
}

function bbcode_format($var) {
    $search = array(
        '/\[phpp\](.*?)\[\/phpp\]/ise',
        );
    $replace = array(
        "varitaPHP('\\1')",
        );
    $var = preg_replace($search, $replace, $var);
    return $var;
}
?>

Näin se toimii sitten tekstissä:

Väritetty PHP-koodi: [phpp]<?php echo 'foo'; ?>[/phpp]

Eli tässä lisättiin tuonne $search -taulukon koodinkorvaajan perään 'e' -lippu, joka ajaa korvattavan tekstin funktion läpi. Lisäksi tehtiin erillinen funktio, joka kutsuu PHP-koodin värittäjää.


Edit. Jep, oli vähän ongelmia Putkan koodinväritystagien kanssa... Täällä on niin paljon aliaksia. :)

tsuriga [07.06.2009 12:10:17]

#

Anna style-määritteen sijaan class ja määrittele ulkoinen css-tiedosto. Nimeäkantamattomat lainaustagisi ovat rikki.

MIB [07.06.2009 12:25:32]

#

Eipä toimi, trilog. Ajattelin tämän olevan vähän helpompi juttu, mutta metsään meni. :/

trilog [07.06.2009 12:26:51]

#

MIB kirjoitti:

Eipä toimi, trilog. Ajattelin tämän olevan vähän helpompi juttu, mutta metsään meni. :/

Kyllä itselläni väritteli hyvin kun testailin...?

Edit. http://codepad.org/nNe1Mc4J

MIB [07.06.2009 12:31:01]

#

Miten kirjoitit tuon [phpp]...[/phpp]:n? Tai, oikeastaan mihin laitoit sen? Näytätkö kokonaan koodisi miten sait? :/ Minulla ei nyt tunnu sujuvan tämä..

trilog [07.06.2009 12:39:50]

#

MIB kirjoitti:

Miten kirjoitit tuon [phpp]...[/phpp]:n? Tai, oikeastaan mihin laitoit sen? Näytätkö kokonaan koodisi miten sait? :/ Minulla ei nyt tunnu sujuvan tämä..

Samalla tavallahan tuo menee kuin muidenkin tagien kanssa. Tuo minun on pelkistetty versio; lisäilet vain nuo parit rivit omaan koodiisi ja tuon varitaPHP -funktion.

TeNDoLLA [07.06.2009 13:35:05]

#

Nyt täytyy kysyä, että miten tuo 'e' lippu määrittää sen ajettavan funktion? Jos samassa tiedostossa on vaikka 50 funktiota, mistä se tietää mikä on oikea jos ei sitä mitenkään osoiteta sille? Eikä sitä funktiota tuossa mitenkään selvästi kutsutakkaan mun mielestä.

trilog [07.06.2009 13:43:39]

#

TeNDoLLA kirjoitti:

Nyt täytyy kysyä, että miten tuo 'e' lippu määrittää sen ajettavan funktion? Jos samassa tiedostossa on vaikka 50 funktiota, mistä se tietää mikä on oikea jos ei sitä mitenkään osoiteta sille? Eikä sitä funktiota tuossa mitenkään selvästi kutsutakkaan mun mielestä.

Vähän epäselvästi tosiaan kirjoitin tuon (itse asiassa sehän ajaa sen PHP-tulkin läpi), ks. https://www.ohjelmointiputka.net/oppaat/opas.php?tunnus=phpsl#tyylikkaitakorvauksia

TeNDoLLA [07.06.2009 13:53:22]

#

Kiitos selvennyksestä. En muuten äsken huomannutkaan, mutta kyllähän siellä tosiaan kutsutaankin tuota funktiota. Ei sattunut silmään kun se oli tuolla stringin "seassa".

Edit: Tuo e-lippu on ilmeisesti sama kuin eval()? Eli onko tuossa mahdollista, että kaikki mitä käyttäjä kirjoittaa ajetaan php tulkin läpi?

MIB [07.06.2009 14:14:47]

#

&lt;?php
echo \"Hello World!\";
?&gt;

Tämäkö on tarkoitus tulla koodista? :/ Ei nyt kyllä ihan toimi.

trilog [07.06.2009 14:17:26]

#

MIB kirjoitti:

<?php
echo \"Hello World!\";
?>

Tämäkö on tarkoitus tulla koodista? :/ Ei nyt kyllä ihan toimi.

stripslashes ja html_entity_decode sitten tuonne funktioon (varitaPHP) jos tuollaisia tulee. Tarkoitus ja tulostus selviää em. codepad-pastesta.

MIB [07.06.2009 14:19:22]

#

Mihin kohtaan? :/

trilog [07.06.2009 14:21:45]

#

MIB kirjoitti:

Mihin kohtaan? :/

<?php
function varitaPHP($s) {
    return '<div style="border-style:solid;border-width:1px;background:white">'.
           highlight_string(html_entity_decode(stripslashes($s)), True).
           '</div>';
}
?>

MIB [07.06.2009 14:34:15]

#

Jaa, tuonne :D Kiitos.
Jostain syystä se tekee alkuun ja loppuun tyhjät rivit... Miten nämä saisi pois? <nobr> -tageja koitin jo...

MIB [07.06.2009 16:12:58]

#

SELECT
  a.id,
  a.otsikko,
  v.lahettaja_id,
  v.aika,
  v.viesti
FROM
  AiheetViimeisinViesti a LEFT JOIN
  viestit v ON a.viesti_id=v.viesti_id
ORDER BY
  a.id

Miten saan lisättyä tähän aliaksen ai? Koitin laittaa tuonne FROM kohdan viestit v ON a.viesti_id=v.viesti_id:n perään aiheet ai, mutta ei toiminut. Miten kuuluisi laittaa?
Haluaisin sen siis, että ai aliaksella olevat tiedot haetaan aiheet taulusta.

tsuriga [07.06.2009 16:56:14]

#

http://wiki.mureakuha.com/wiki/SQL_aloittelijoille

MIB [07.06.2009 17:05:44]

#

tsuriga kirjoitti:

http://wiki.mureakuha.com/wiki/SQL_aloittelijoille

Tuolla ei kerrota, miten tehdään jos on enemmän noita aliaksia. Koitin tehdä esimerkkien mukaan, mutta tekee errorin.

Metabolix [07.06.2009 18:18:28]

#

Olet jäsentänyt lauseesi väärin. Et ilmeisesti ymmärrä kunnolla JOIN-lauseen syntaksia.

SELECT *
FROM taulu AS alias
LEFT JOIN taulu2 AS alias2 ON ehto2
LEFT JOIN taulu3 AS alias3 ON ehto3
WHERE ehto

tsuriga [07.06.2009 18:30:24]

#

Vaikka tuo AS taikasana onkin myslissä vapaaehtoinen niin sen käyttö on suositeltavaa selkeyden (ja portattavuuden?) kannalta. Useamman aliaksen käyttö ei eroa yhden käytöstä lainkaan, kuten yllä on esitetty.

MIB [07.06.2009 21:15:17]

#

Kun en kyselyillä saanut toimiin, niin tein FOR -silmukalla

for ($i = 0; $i < mysql_num_rows($haku); $i++) {
 $lahettaja = mysql_result($haku, $i, "lahettaja_id");
 $otsikko = mysql_result($haku, $i, "otsikko");
 $aika = mysql_result($haku, $i, "aika");
 $aika2 = date("d.m.Y H:i:s", $aika);
  for ($i = 0; $i < mysql_num_rows($haku1); $i++) {
  $aloittaja = mysql_result($haku1, $i, "lahettaja");
  $aikaa = mysql_result($haku1, $i, "aika");
  $aloitettu = date("d.m.Y H:i:s", $aikaa);
  echo "<tr><td>$aloittaja</td><td>$otsikko</td><td>$aloitettu</td><td>$lahettaja</td><td>$aika2</td></tr>";
 }
}

Grez [07.06.2009 22:10:47]

#

Mitkä noi $haku ja $haku1 -kyselyt tuossa on?

Mielestäni aika erikoisesti toteutettu ja tuohan jää ikuiseen looppiin jos $haku1 palauttaa 2 - n riviä vähemmän kuin $haku.

MIB [08.06.2009 07:02:21]

#

$haku ja $haku1 ovat kyselyt, joilla haen tietoa eri tauluista. Sitä pitää vähän vielä parannella, koska se ei saa oikeaa aikaa viimeisimpään viestiin.

Grez [08.06.2009 10:46:00]

#

No sen nyt tajusinkin. Tarkoitin lähinnä: Mitkä ne kyselyt on? Ihan SQL-koodina.

Nykyisellään on vaikeaa kertoa miten tuon voisi tehdä kunnolla, kun ei voi tietää mitä se tekee.

kayttaja-2791 [08.06.2009 11:44:25]

#

...lisäksi vastausintoa lisäisi kummasti jos koodi olisi vielä koodiväritetty (php-koodi alkaa <?php ja loppuu ?>) ja sisennykset olisivat kunnossa... Ihan näin vinkkinä vain :)

MIB [08.06.2009 13:33:54]

#

No joo, Grez: Mulla tuli pieni virhe tossa ajatellessani tota..
JTS: Sisennykset oli kunnossa omassa lähdekoodissani, mutta lysähti tohon. Oisinhan mä tietenkin <?php ?> tagit voinut laittaa...

MIB [08.06.2009 16:00:40]

#

<?php
require_once("settings.php");
$y = mysql_connect("$dbserver", "$dbuser", "$dbpw");
mysql_select_db("$db");

$kysely1 = "SELECT
  a.id,
  a.otsikko,
  a.lahettaja,
  v.aika,
  Max(v.aika) ViimeisinViesti
FROM
  Aiheet a
  JOIN viestit v ON (v.aihe_id=a.id)
GROUP BY
  a.id,
  a.otsikko
ORDER BY
  Max(v.aika) DESC";
$haku1 = mysql_query($kysely1) or die(mysql_error());

$kysely = "
SELECT
  a.id,
  a.otsikko,
  v.lahettaja_id,
  v.aika,
  v.viesti
FROM
  AiheetViimeisinViesti a LEFT JOIN
  viestit v ON a.viesti_id=v.viesti_id
ORDER BY
  a.id

";
$haku = mysql_query($kysely) or die(mysql_error());
echo '<table class="teksti" width="95%" cellspacing="0">';
echo '<tr class="taulukkoyla">
<td width="40%"><b>Aiheen otsikko</b></td>
<td><b>Aloittaja</b></td>
<td><b>Viimeisin</b></td></tr>';

for ($i = 0; $i < mysql_num_rows($haku); $i++) {
  for ($i = 0; $i < mysql_num_rows($haku1); $i++) {
  $aloittaja = mysql_result($haku1, $i, "lahettaja");
  $aikaa = mysql_result($haku1, $i, "aika");
  $aloitettu = date("d.m.Y H:i:s", $aikaa);
  $aika = mysql_result($haku, $i, "aika");
  $aika2 = date("d.m.Y H:i:s", $aika);
  $lahettaja = mysql_result($haku, $i, "lahettaja_id");
  $otsikko = mysql_result($haku, $i, "otsikko");
  $id = mysql_result($haku, $i, "id");
  echo "<tr><td width='35%'><a href=\"index.php?sivu=alue&aiheid=$id\">$otsikko</a></td><td>
  <a href=\"index.php?sivu=profiili&tunnus=$aloittaja\">$aloittaja</a></td>
	<td><a href=\"index.php?sivu=profiili&tunnus=$lahettaja\">$lahettaja</a> / $aika2</td></tr>";
 }
}
echo "</table>";
mysql_close($y);
?>

Tämmöinen, ei toimi tuo $aika2. Muut toimivat, vaikka aika hirveän näköinen sotku tuo onkin. En vaan keksi miten voisin tehdä samaan kyselyyn nuo...

MIB [09.06.2009 18:36:18]

#

Ongelma haun kanssa:
Tein tälläisen haun, mikä hakee viesteistä aikajärjestyksessä ne, joissa esiintyy kyseinen hakusana. Ongelmana on se, että jos samasta aiheesta löytyy useampi viesti, joissa on tämä hakusana, vain aloitusviestissä näkyy otsikko (siis, jos hakusana löytyy aloitusviestistä).

<?php
require_once("ylaosa.php");

$hakusana = $_GET["hae"];
$hakukysely = "
SELECT * FROM viestit WHERE viesti LIKE '%$hakusana%' ORDER BY aika DESC LIMIT 100";
$haku = mysql_query($hakukysely) or die(mysql_error());

$alue = "Yleinen keskustelu";
echo "<table>";
for ($i = 0; $i < mysql_num_rows($haku); $i++) {
$otsikko = mysql_result($haku, $i, "otsikko");
$lahettaja = mysql_result($haku, $i, "lahettaja_id");

echo "<tr><td>$alue:</td><td>$otsikko</td></tr>";
}
echo "</table>";
require_once("alaosa.php");
?>

MIB [09.06.2009 21:44:54]

#

Tiedän ettette pidä siitä, että lähetän niin paljon kysymyksiä, joita pidätte päivänselvänä asiana (Olettehan te ohjelmoinneet kauemmin kuin minä. Ei minun ikääni millään mahdu niin paljon taitoa), mutta en ole saanut millään toimimaan.
Siispä, kysyn tuota ylläolevaa uusiksi.

Teuro [09.06.2009 21:54:00]

#

Haluan tarkentaa kysymystä, joten miten tuon sinusta tulisi toimia? Oletamme, että kannassa on samassa langassa kaksi viestiä, joissa on sanana vaikkapa 'moikka'. Nyt jos teemme haun sanalle 'moikka', niin mitä tuon tulee tulostaa?

MIB [09.06.2009 21:58:29]

#

Lähettäjä1: aihe1
Lähettähä2: aihe1
Lähettäjä1: aihe5

Jokaisessa pitäisi lukea aiheen otsikko, vaikka ne samaan kuuluisivat. Tuo äskeinen tulostuu omalla skriptillä näin.

Lähettäjä1: aihe1
Lähettäjä2:
Lähettäjä1: aihe5

Teuro [09.06.2009 22:03:08]

#

<?php
echo "<tr><td>$alue:</td><td>$otsikko</td></tr>";
?>

Eihän tuolla koodilla ole mitenkään mahdollista saada pyydettyä tulostetta?

MIB [09.06.2009 22:05:58]

#

<?php
require_once("ylaosa.php");

$hakusana = $_GET["hae"];
$hakukysely = "
SELECT * FROM viestit WHERE viesti LIKE '%$hakusana%' ORDER BY aika DESC LIMIT 100";
$haku = mysql_query($hakukysely) or die(mysql_error());

echo "<div style=\"padding-left: 10px\">";
if(!empty($hakusana)) {
echo "<table><tr><td><b>Keskusteluista löytyi:</b></td></tr><tr></tr><tr></tr>";
for ($i = 0; $i < mysql_num_rows($haku); $i++) {
$otsikko = mysql_result($haku, $i, "otsikko");
$lahettaja = mysql_result($haku, $i, "lahettaja_id");
$aiheid = mysql_result($haku, $i, "aihe_id");

echo "<tr><td>$lahettaja kirjoitti viestin aiheeseen:</td><td><a href=\"alue.php?aiheid=$aiheid\">$otsikko</a></td></tr>";
}
echo "</table>";
} else echo '<br><b>Et täyttänyt hakusanaa!</b> Sinun pitää täyttää se hakeaksesi tietoa.<br><br><form action="haku.php" method="GET">
<input type="name" name="hae"> <input type="submit" value="Hae"></form>';
echo "</div>";
require_once("alaosa.php");
?>

Näinhän se on tehty: ei toimi. En ole varma, mutta taidan tietää mistä ongelmani johtuu. Katson tuolla PhpMyAdminilla mitä tietokannoissa lukee.. Luulen että olen vaivannut turhaan. Uskoisin, että vain aloitusviestissä lukee otsikko, ja muut ovat NULL arvolla.

MIB [10.06.2009 13:34:13]

#

Mun moka oli, en muistanut muuttaneeni vastauskoodia noin paljon, että ei kirjoita aiheen otsikkoa.
No, nyt se siis toimii, paitsi yhtä juttua lukuunottamatta:
Jos hakutuloksia ei löytynyt, se ei palauta mitään muuta kuin "Keskustelusta löytyi:" -tekstin. Muistaakseni mysql_num_rows:lla voi tarkistaa, mutta en muista miten se oli ja missä törmäsin siihen. Muuten, jos hakutuloksia ei löytynyt (mysql_num_rows), niin minkä arvon se palauttaa kyselystä?

Edit: Keksimpä jo miten teen sen.

<?php
if (mysql_num_rows($haku) == 0) echo "<tr><td>Ei löytynyt tuloksia</td></tr>";
?>

MIB [10.06.2009 19:42:31]

#

Ja vielä kolmas viesti peräkkäin... (:s)
Nyt tarvitsisin sellaisen systeemin, että kun yhdelle sivulle otetaan vaan 15 uusinta aihetta, niin jos on yli, niin tulisi seuraava sivu jossa olisi seuraavat 15. Niinkuin Putkassa. Nyt ei ole yhtään hajua, miten tämä tehdään.
Osaisin varmaan tehdä loput, mutta sitä en, kun tulostus katkaistaan 15 jälkeen, niin seuraavalla sivulla jatkuisi 16 eteenpäin...

Tumettaja [10.06.2009 19:45:21]

#

Oletko jo lukenut putkassa olevan koodivinkin tuollaisen systeemin toteutuksesta?

MIB [10.06.2009 19:49:53]

#

Hee, en olekkaan huomannut tuota. Kiitos vinkistä!

MIB [10.06.2009 22:22:05]

#

Miten saisin katkaistua yli 10 merkkiä pitkät merkinnät? Menee vähän huonosti tuo ulkoasu niin pitkillä sanoilla....

temu92 [11.06.2009 01:03:48]

#

<?php
    $str = substr($str, 0, 10);
?>

Taikasana substr.

MIB [11.06.2009 08:07:14]

#

Ongelmana tuossa on, kun otan ensin uusimmasta viestistä 200 ensimmäistä merkkiä ja $str olisi ne 200 merkkiä, niin tuo katkaisisi sen 10 merkin pituiseksi. Siis, jos on vaikka teksti "Minä olen Pekka ja aaaaaaaaaasun maatilalla eläimieni kanssa.", niin tuo tummennettu sana katkaistaisiin, ja laitettaisiin <br> siihen 10:n merkin jälkeen, jolloin olisi

aaaaaaaaaa
sun

Tajusittekos?

Metabolix [11.06.2009 08:58:20]

#

Oletko nyt ajatellut asian loppuun asti?

Minä olen Pekka ja
aaaaaaaaaa
sun maatilalla eläimieni
kanssa.

Paremmin tarkoitukseen sopisi oikein sijoiteltu &shy; eli tavuviiva, jonka kohdalta selain voi tarvittaessa tavuttaa sanan automaattisesti. Tämän tuki alkaa kai nyt olla jo käytettävällä tasolla, aiemmin monet selaimet eivät ymmärtäneet merkintää. Laatikkoa varten tyydyttävästi toimivan suomen tavutuksen saa aikaan säännöllisillä lausekkeilla muutamalla koodirivillä, kun hieman pohtii tavutussääntöjä.

Samaisilla lausekkeilla onnistuu myös haluamasi 10 merkin katkaisu. Tässä laitan siihen tavuviivan.

<?php
$t = preg_replace('/\\w{10}(?=\\w)/', '\\0-', $t);

Edit. Kohtalaiseen tavutukseen riittää jopa tällainen:

<?php
$vok = "aeiouyåäöAEIOUYÅÄÖ";
$kon = "bcdfghjklmnpqrstvwxzBCDFGHJKLMNPQRSTVWXZ";
// Tavutetaan ennen konsonanttia, jos sen jälkeen tulee vokaali.
// Suurin osa tavurajoista on näitä, mutta tiettyjen vokaaliparien väliin
// pitäisi myös laittaa viiva, ja esim. maanalainen tavuttuu väärin.
$t = preg_replace("/([$kon$vok])(?=[$kon][$vok])/", '\\0&shy;', $t);

// Katkotaan vielä varmuuden vuoksi liian pitkät kirjainjonot,
// jotka eivät edellisellä katkenneet.
$t = preg_replace('/\\w{10}(?=\\w)/', '\\0&shy;', $t);

MIB [11.06.2009 14:46:37]

#

Kiitos, nyt on todella ärsyttävä ongelma.
Kun aiheita tulee foorumeille yleensä niin paljon, että niitä ei jaksa alkaa selata yhdellä sivulla, niin tuota Antin sivutus koodivinkkiä käytin.
Nyt pitäisi luoda toinen alue. Aiheissa on alue_id sarake, jolla viestit kuuluisi ohjata oikeaan paikkaan. Kysely, jossa ei ole sivutusta, toimii:

<?php
require_once("yla.php");
require_once("ylaosa.php");
$ky = "SELECT * FROM aiheet WHERE alue_id = '2'";
$ha = mysql_query($ky);

echo '<table class="teksti" width="95%" cellspacing="0">';
echo '<tr class="taulukkoyla">
<td width="50%"><b>Aiheen otsikko</b></td>
<td width="20%"><b>Aloittaja</b></td>
<td><b>Aloitusaika</b></td></tr>';

for ($i = 0; $i < mysql_num_rows($ha); $i++) {
$otsikko = mysql_result($ha, $i, "otsikko");
$lahettaja = mysql_result($ha, $i, "lahettaja");
$aika = mysql_result($ha, $i, "aika");
$aikaa = date("d.m.Y H:i:s", $aika);
$id = mysql_result($ha, $i, "id");

echo "<tr><td><a href=\"alue.php?aiheid=$id\">$otsikko</a></td><td>$lahettaja</td><td>$aikaa</td></tr>";
}
echo "</table>";

?>
<div style="padding-left: 10px">
</div>

<?php
require_once("alaosa.php");
?>

Mutta, tämä ei toimikkaan, mikä pitäisi saada kuntoon:

<?php
require_once("yla.php");
require_once("ylaosa.php");
$vps = 15;

// luetaan osoitteen mukana tullut sivunumero
if (isset($_GET['sivu'])) {
    $sivu = $_GET['sivu'];
}
$sivu = intval($sivu);

// haetaan näytettävät viestit tietokannasta
$viestit = mysql_query("SELECT
  a.id,
  a.otsikko,
  a.lahettaja,
  a.alue_id,
  v.aika,
  Max(v.aika) ViimeisinViesti
FROM
  Aiheet a
  JOIN viestit v ON (v.aihe_id=a.id)
WHERE
  a.alue_id = '2'
GROUP BY
  a.id,
  a.otsikko
ORDER BY
  Max(v.aika) DESC
LIMIT ".($sivu * $vps).", {$vps}");

// selvitetään viestien määrä
$maara = mysql_result(mysql_query("SELECT COUNT(*) FROM aiheet"), 0);


 if ($maara > $vps) {
  echo '<p class="teksti" align="right">Sivut: ';
    for ($i = 0; $i < $maara / $vps; $i++) {
        if ($i <> 0) {
            echo " ";
        }
        // jos tämä sivu näytetään, tulostetaan sivun numero lihavoituna
        if ($sivu == $i) {
            echo "<b>".($i + 1)."</b>";
        // muussa tapauksessa luodaan linkki toiselle sivulle
        } else {
            echo "<a href=\"{$_SERVER['PHP_SELF']}?sivu={$i}\">".($i + 1)."</a>";
        }
    }
} echo "</p>";
echo '<table class="teksti" width="95%" cellspacing="0">';
echo '<tr class="taulukkoyla">
<td width="50%"><b>Aiheen otsikko</b></td>
<td width="20%"><b>Aloittaja</b></td>
<td><b>Aloitusaika</b></td></tr>';
// tulostetaan tietokannasta luetut viestit
for ($i = 0; $i < $vps; $i++) {
    // varmistetaan, että viimeisellä sivulle ei tule ylimääräistä
    if ($i + $sivu * $vps < $maara) {
        // tulostetaan viestin tiedot yksinkertaisesti muotoiltuna
		$aihe_id = mysql_result($viestit, $i, "id");
        $aika = mysql_result($viestit, $i, "aika");
		$aika2 = date("d.m.Y H:i:s", $aika);
        $nimi = mysql_result($viestit, $i, "lahettaja");
        $otsikko = mysql_result($viestit, $i, "otsikko");
        echo "<tr>
	    <td><a href=\"alue.php?aiheid=$aihe_id\">$otsikko</a></td>
	    <td><a href=\"ohjaus.php?tunnus=$nimi\">$nimi</a></td>
	    <td>$aika2</td></tr>";
    }
} echo "</table>";

?>
<div style="padding-left: 10px">
</div>

<?php
require_once("alaosa.php");
?>

jo123 [12.06.2009 05:15:46]

#

Anteeksi jos vastaan hieman kuuseen, mutta kun haet aiheiden määrän, niin onkohan sittenkään tarkoituksesi hakea kaikki aiheet taulun aiheet, vai pelkästeen kyseisen foorumin. Eli jos olen oikeassa, niin pitäisi muuttaa $maara-kysely tälläiseksi:

select count(*) from aiheet where alue_id="haluamasi id"

MIB [12.06.2009 09:16:42]

#

Se auttoi kovasti :) Kiitos sinulle, nyt toimii kunnolla. Heh

MIB [12.06.2009 17:26:48]

#

Vielä yksi juttu, sitten on minun mielestä tämä foorumini valmis:
Tarvitsisi saada näkyviin viestien määrä eri alueilla (Niinkuin Putkassa), ja viimeisimmän viestin lähettäjä & aika per alue.

Näin saan tulostettua alueet ja aiheiden määrän per alue, mutta en noita muita, koska ne eivät ole samassa taulussa.

<?php
require_once("yla.php");
require_once("ylaosa.php");

mysql_query("CREATE TABLE alueet(
id INT UNSIGNED AUTO_INCREMENT NOT NULL PRIMARY KEY, alue TEXT, tiedosto TEXT)");
$ky = "SELECT * FROM alueet";
$ha = mysql_query($ky) or die(mysql_error());


//Luodaksesi uuden aiheen, mene luoalue.php tiedostoon

echo '<table class="teksti" width="95%" cellspacing="0">
<tr class="taulu">
<td><b>Alue</b></td><td><b>Aiheita / Viestejä</b></td><td><b>Uusin viesti</b></td>
</tr>';
for ($i = 0; $i < mysql_num_rows($ha); $i++) {
$alue = mysql_result($ha, $i, "alue");
$id = mysql_result($ha, $i, "id");

$ky2 = "SELECT * FROM aiheet WHERE alue_id = '$id'";
$ha2 = mysql_query($ky2) or die(mysql_error());


$a = mysql_num_rows($ha2);

echo "<tr><td><a href=\"alueet.php?alue=$id\">$alue</a></td>
<td>$a / Viestejä</td><td><br>Viimeisin viesti<br><br></td></tr>";

}
echo "</table>";
require_once("alaosa.php");
?>

Koska viestit yhdistetään aiheisiin aihe_id:n perusteella, ja aiheet alueisiin alue_id:n perusteella, niin en tiedä miten 'yhdistäisin' eri tauluista tietoa.

Ps. Noissa includetuissa sivuissa ei ole kuin ulkoasu & mysql_connect hömpät.

MIB [12.06.2009 19:43:57]

#

Tohon vielä lisään helpottamaan taulujen rakenteet:

alueet
  id (Alueen numero, 1, 2, 3 jne...)
  alue (Alueen nimi.)

viestit
  viesti_id (Monesko viesti)
  aihe_id (Aiheen id, mihin on lähetetty)
  id (Lähettäjän id numero)
  lahettaja_id (Lähettäjän tunnus)
  aika (Milloin lähetetty)
  otsikko (Aiheen otsikko mihin lähetetty)
  viesti (Viesti)

aiheet
  alue_id (Mihin alueeseen on, viitataan aluuet taulun id:seen)
  id (Monesko, 1, 2, 3... jne)
  otsikko (Aiheen otsikko)
  aika (Milloin aloitettu)
  lahettaja (Lähettäjän nimi)
  lahettaja_id (Lähettäjän id numero)

Osaisiko joku nyt auttaa? =)

jo123 [13.06.2009 04:57:26]

#

Avainsana on sql:än join-kyselyt. Ideana on siis että yhdistetään monesta taulusta tietoa yhteen uuteen väliaikaiseen(temp) tauluun. Kun siis haluat hakea lahettaja_id:n ja aika kentän viestit taulusta aiheet-taulun alue_id:n avulla (tai jotain sinne päin XD). Oli mikä oli kyselysi pitää kuitenkin olla tälläinen:

select lahettaja_id,aika from viestit join aiheet on viestit.aihe_id=aiheet.id and aiheet.alue_id="haluamasi alue_id"

Sitten tosta vaan mysql_num_rows:lla viestien määrä.

MIB [13.06.2009 15:33:57]

#

Empä näin saanut toimimaan.
Tiedän miten saan kaikista alueista yhteismäärän, mutta ei auta tässä.
Koitin vääntää tuon sinun vinkin pohjalta, mutta ei onnistunut.
Nyt näyttää tältä:

<?php
include("ylaosa.php");

$k = "SELECT COUNT(*) FROM viestit GROUP BY aihe_id";
$h = mysql_query($k) or die(mysql_error());

echo "".mysql_num_rows($h)."<br>";
include("alaosa.php");
?>

(Tämän on tarkoitus vain hakea se viestien määrä aluksi, sillä hoksasin juuri, miten haen viimeisimmän viestin lähettäjän ja aiheen otsikon per alue.)

Edit: Heh, sain valmiiksi lisäämällä GROUP BY aihe_id:n kyselyn loppuun.

SELECT * FROM viestit JOIN aiheet ON viestit.aihe_id=aiheet.id AND aiheet.alue_id='1' GROUP BY aihe_id

Edit: Ja vähän vielä muuttamalla (oikeastaan palautin tuon jo123:n kyselyn), sain toimimaan niinkuin halusin.

<?php
require_once("yla.php");
require_once("ylaosa.php");

mysql_query("CREATE TABLE alueet(
id INT UNSIGNED AUTO_INCREMENT NOT NULL PRIMARY KEY, alue TEXT, tiedosto TEXT)");
$ky = "SELECT * FROM alueet";
$ha = mysql_query($ky) or die(mysql_error());


//Luodaksesi uuden aiheen, mene luoalue.php tiedostoon

echo '<table class="teksti" width="95%" cellspacing="0">
<tr class="taulukkoyla">
<td><b>Alue</b></td><td><b>Aiheita / Viestejä</b></td><td><b>Uusin viesti</b></td>
</tr>';
for ($i = 0; $i < mysql_num_rows($ha); $i++) {
$alue = mysql_result($ha, $i, "alue");
$id = mysql_result($ha, $i, "id");

$ky2 = "SELECT * FROM aiheet WHERE alue_id = '$id'";
$ha2 = mysql_query($ky2) or die(mysql_error());

$k = "SELECT * FROM viestit JOIN aiheet ON viestit.aihe_id=aiheet.id AND aiheet.alue_id='$id'";
$h = mysql_query($k) or die(mysql_error());

$a = mysql_num_rows($ha2);
$v = mysql_num_rows($h);

echo "<tr><td><a href=\"alueet.php?alue=$id\">$alue</a></td>
<td>$a / $v</td><td><br>Viimeisin viesti<br><br></td></tr>";

}
echo "</table>";
require_once("alaosa.php");
?>

jo123 [13.06.2009 17:53:40]

#

No hyvä. Oikeastaan tuo kyselyni haki tietyn alueen kaikki viestit, joten se ei oikeastaan ollut aivan tarkasti se mitä halusit. Sillä sai kuitenkin haettua alueen viestien määrän, niin kuin itsekin jo huomasit. Kyselyä säätämällä saa sitten vielä haettua uusimman viestin ajan ja lähettäjän. ;)

MIB [13.06.2009 17:57:54]

#

Tuo toimii nyt noin, mutta tulikin mietittyä uudelleen sitä viimeisimmän viestin lähettäjää, aikaa ja otsikkoa. Se ei mennytkään ihan niin helposti kuin ajattelin.
Koitin laittaa näin:

SELECT * FROM viestit JOIN aiheet ON viestit.aihe_id=aiheet.id AND aiheet.alue_id='$alue_id' GROUP BY aihe_id ORDER BY viestit.aika DESC LIMIT 1

Tämä vain sattuu näyttämään lähettäjän tiedot joka on aloittanut aiheen. Kylläkin näyttää silti siitä aiheesta mihin on vastattu viimeiseksi.
Osaisiko joku vielä auttaa? :D

Edit: Taas tuli kysyttyä, ennen kuin ajateltua. Otimpa vain tuon GROUP BY -jutun pois, niin se oli siinä.
Silti en saa niin, että näkyis jokaisessa alueessa uusin viesti. Hetki menee vielä varmaan vääntää.

MIB [16.06.2009 11:57:16]

#

Tuli tässä taas pieni ongelma, kun haku systeemissäni voi hakea joko erikseen jäsenistä tai keskusteluista tms. tai sitten kaikista. Ongelma on siinä, että miten haen kaikista? Koska, jäsenet ja keskustelut ovat eri tauluissa, niin siinä on se ongelma. SELECT * FROM voiko,taulut,erottaa,näin ORDER BY aika DESC?

Metabolix [16.06.2009 12:06:08]

#

Ei kuulu tehdä noin, et saa lainkaan järkeviä tuloksia. (Lue jostakin, kuinka monen taulun kyselyt toimivat.) Järkevintä on tehdä kaikki haut erikseen ja tulosta tulokset erikseen, koska eihän noissa tauluissa ole riittävästi yhteistä, jotta niistä voisi järkevästi tehdä saman haun.

MIB [16.06.2009 12:24:05]

#

Nojoo, tehdään sitten niin.

Nyt tuli toisenlainen "ongelma". Minun pitäisi lisätä noin 600 riviä tietoa tietokantaan. Jokainen rivi on erillainen, ja taulussa on kolme kohtaa.
Miten saisin tehtyä sellaise ns. listan joka sitten kirjoitetaan?
Voisiko tehdä niin, että kirjoitan tekstitiedostoon ensin (taino, ne on jo kirjoitettu) tiedot, sitten explodella erottelen, ja kirjoitan ne?

Teuro [16.06.2009 12:29:09]

#

Voit toki tehdä noin, mutta kannatta olla sitten ihan varma mitä olet tekemässä, koska tuon kyselyryppään pitää onnistua oikein. Melkein suosittelen ensin preparoimaan koko roskan sopivaan muotoon vaikkapa valmiiksi kyselyiksi ja tulostamaan ne näytille.

Missä muodossa tallennettavat tiedot ovat?

MIB [16.06.2009 12:36:15]

#

Teuro kirjoitti:

Missä muodossa tallennettavat tiedot ovat?

Siis, ihan tekstinä on.
Sanoinkin väärin, pitäisi täyttää numero ja nimi tauluun..

Teuro [16.06.2009 12:51:18]

#

Elikä tyyliin:

15|Juha
20|Pete
.
.
.

Jos näin, niin tuosta pitäisi sitten muodostaa n kyselyä, jotka ajetaan luupissa kantaan. 300 riviä taitaa olla niin pieni määrä, että normaali file(string) + explode(erotin, rivi) voisi olla sopiva parivaljakko, jolla tehtävän saisi suoritettua. Mahdollisesti data kannattaa siivota mysql_real_escape_string(string) funktiolla turvallisemmaksi?

MIB [16.06.2009 12:54:37]

#

Tämä nyt ei ole se koodi, mutta tähän tyyliin?

<?php
$akuankat = file("akuankat.txt");

for ($i = 0; $i < $viestimaara; $i++) {
   $tiedot = explode("|", $akuankat[$i], 2);

   //erotellaan tiedot omiin muuttujiinsa
   $numero = $tiedot[0];
   $nimi = $tiedot[1];
   mysql_query("INSERT INTO taskukirjat(numero, nimi) VALUES('$numero', '$nimi')") or die(mysql_error());

}
?>

Tein tollaisen kerran...

Teuro [16.06.2009 12:58:38]

#

Viestimäärä on tuntematon muuttuja. Tuossahan ajat sitten koko roskan laakista kantaan sen kummemmin tutustumatta sisältöön etukäteen, joka voisi olla ihan järkevää. Lisäki numerokenttä lienee (INT) tyyppinen, jolloin hipsuja ei ole tarkoitus käyttää.

MIB [16.06.2009 13:01:10]

#

Jäi mun copy pastesta se viestimaara pois...
Joo, numero on INT tyyppinen. Miten se kuuluisi sitten tehdä?

Teuro [16.06.2009 13:10:22]

#

<?php
$akuankat = file("akuankat.txt");
$viestimaara = count($akuankat);

for ($i = 0; $i < $viestimaara; $i++) {
   $tiedot = explode("|", $akuankat[$i]);

   //erotellaan tiedot omiin muuttujiinsa
   $numero = $tiedot[0];
   $nimi = $tiedot[1];
   $kysely[] = "INSERT INTO taskukirjat(numero, nimi) VALUES($numero, '$nimi')";
}

for($a = 0; $a < count($kysely); $a++){
    echo $kysely[$a] . "<br />";
}
?>

MIB [16.06.2009 14:28:27]

#

Kiitos :)

MIB [17.06.2009 12:56:25]

#

Nyt kun tuon sain tehtyä (muutettua Teuron esimerkistä), niin tuli toinen juttu:
Kun minulla on monta aluetta foorumilla, niin selkeyttäisi lukemista, kun olisi niillä <tr> tageilla taustaväri. Niinkuin täälläkin, joka toinen on värillisellä pohjalla.
Joskus onnistuin säätämään jotain niin, että tulisi, mutta se oli niin pahaa siansaksaa, että huhhuh.

Teuro [17.06.2009 13:02:56]

#

<?php
$a = 0;
while($rivi = mysql_fetch_array($tulos)){
    echo"<tr>";
    $vari = ($a % 2 == 0) ? 'punainen' : 'vihrea';
    echo"<td class=\"$vari\">".$rivi['otsikko']."</td>";
    $a++;
    echo"</tr>";
}

Ei niin kamalan hankalaa eihän?

MIB [17.06.2009 13:05:13]

#

Kiitos sulle taas. Pitänee varmaan tutustua paremmin WHILE ja FOR silmukoihin.

MIB [17.06.2009 14:15:50]

#

Mullapa onkin tänään paljon kysymyksiä mielessä.
Kun tuossa ajv:n koodivinkissä käytetään sessioneja, niin minun pitäisi saada muutettua ne kekseiksi.
Koitin näin. Se näyttäisi kirjaavan tuon id:n ylös, mutta se ei päästä sisään.
Keksiin siis menee se id, mutta ei kirjaudu sisään.

<?php
include("config.php"); //muuta config.php:n polku oikeaksi
//avataan yhteys tietokantaan
$lnk = mysql_connect($db_server,$db_user,$db_passwd) or die ("Yhteys tietokantaan epäonnistui");
mysql_select_db($db_db,$lnk) or die ("Tietokannan valitseminen epäonnistui");

//käyttäjä on oletuksena false. Älä varsinkaan poista, ellet tiedä mitä teet :)
$user = false;


/* SISÄÄNKIRJAUTUMINEN */
if(isset($_POST['tunnus']) && isset($_POST['salasana'])){

   //muuttujat turvallisesti talteen
   $tunnus = get_magic_quotes_gpc() ? $_POST['tunnus'] : mysql_real_escape_string($_POST['tunnus']);
   $salasana = get_magic_quotes_gpc() ? $_POST['salasana'] : mysql_real_escape_string($_POST['salasana']);
   $salasana = md5($salasana);

   //luodaan käyttäjäkohtainen uniikki id
   $istuntotunnus = md5(uniqid(""));
   //lisätään istunto tietokantaan käyttäjän tietoihin
   mysql_query("UPDATE {$tbl_users}
   SET istunto = '{$istuntotunnus}'
   WHERE tunnus = '{$tunnus}'
   AND salasana = '{$salasana}'",$lnk) or die (mysql_error());
   if(mysql_affected_rows($lnk) == 1){
      setcookie("log_key", "$istuntotunnus");
      echo "Katsotaan onko kirjauduttu (Päivitä, näkyykö cryptattu id?): " . $_COOKIE["log_key"] . "";
   }
}

/* ULOSKIRJAUTUMINEN */
if(isset($_REQUEST['logout'])){

setcookie("log_key", "");
setcookie("log_key", "", time() - 60 * 10);
   echo "Logget out";
}


/* KÄYTTÄJÄN TUNNISTUS */
if(isset($_COOKIE['log_key'])){

   //HAETAAN KÄYTTÄJÄN TIEDOT
   $sql = "SELECT
   id,
   tunnus,
   DATE_FORMAT(last_load,'%d.%m.%y %h:%i:%s') AS last_load
   FROM {$tbl_users}
   WHERE istunto = '".mysql_real_escape_string($_COOKIE['log_key'])."'";
   $sql = mysql_query($sql,$lnk);
   if($sql && mysql_num_rows($sql) == 1){
      $user = mysql_fetch_assoc($sql);
      mysql_query("UPDATE {$tbl_users} SET
      last_load = NOW()
      WHERE id = ".$user['id'], $lnk);

   }


}
mysql_query("CREATE TABLE IF NOT EXISTS `{$tbl_users}` (
  id int(11) NOT NULL auto_increment,
  tunnus varchar(50) default NULL,
  salasana varchar(32) default NULL,
  oikeanimi TEXT,
  email varchar(60) default NULL,
  ika INT,
  kotisivu TEXT,
  kuvaus TEXT,
  last_load timestamp(14) NOT NULL,
  istunto varchar(32) default NULL,
  PRIMARY KEY  (id),
  UNIQUE KEY istunto (istunto)
)",$lnk);

Ongelma taitanee johtua tuosta käyttäjän tunnistuksesta.

Teuro [17.06.2009 15:08:23]

#

Katsopa mitä noihin erilaisiin muuttujiin on tallentunut, sen jälkeen askel kerrallaan katsomaan missä kohdin menee metsään. Taulun rakenne lienee oikein, jos olet ajanut tuon ajv:n scriptin läpi virheittä.

Sisään kirjautuessa teet taas kerran suoraan kantaan ajamisen SQL-lauseella, jonka sisällöstä ei ole tietoa. Tulosta se ja katso onko sisältö oikein. Samalla tyylillä kaikki muutkin muuttujat läpi. Jokaisen mysql_query(string) funktion jälkeen olisi hyvä olla echo mysql_error(), joka kertoo suoraan varsinaiset syntaksivirheet.

Kehitysvaiheessa kannattaa tulostaa mahdollisimman monen muuttujan arvo näytille, koska monasti virhe löytyy sillä tavalla helpommin.

MIB [17.06.2009 15:14:08]

#

Mikään kysely ei tee virhettä, kirjautuessa kaikki tiedot kirjataan oikein kantaan, mutta käyttäjän tunnistus uupuu.
Sitä en saa mistään...

<?php
include("config.php"); //muuta config.php:n polku oikeaksi
//avataan yhteys tietokantaan
$lnk = mysql_connect($db_server,$db_user,$db_passwd) or die (mysql_error());
mysql_select_db($db_db,$lnk) or die (mysql_error());

//käyttäjä on oletuksena false. Älä varsinkaan poista, ellet tiedä mitä teet :)
$user = false;


/* SISÄÄNKIRJAUTUMINEN */
if(isset($_POST['tunnus']) && isset($_POST['salasana'])){

   //muuttujat turvallisesti talteen
   $tunnus = get_magic_quotes_gpc() ? $_POST['tunnus'] : mysql_real_escape_string($_POST['tunnus']);
   $salasana = get_magic_quotes_gpc() ? $_POST['salasana'] : mysql_real_escape_string($_POST['salasana']);
   $salasana = md5($salasana);

   //luodaan käyttäjäkohtainen uniikki id
   $istuntotunnus = md5(uniqid(""));
   //lisätään istunto tietokantaan käyttäjän tietoihin
   mysql_query("UPDATE {$tbl_users}
   SET istunto = '{$istuntotunnus}'
   WHERE tunnus = '{$tunnus}'
   AND salasana = '{$salasana}'",$lnk) or die (mysql_error());
   if(mysql_affected_rows($lnk) == 1){
      setcookie("log_key", "$istuntotunnus");
      echo "Katsotaan onko kirjauduttu (Päivitä, näkyykö cryptattu id?): " . $_COOKIE["log_key"] . "";
   }
}

/* ULOSKIRJAUTUMINEN */
if(isset($_REQUEST['logout'])){

setcookie("log_key", "");
setcookie("log_key", "", time() - 60 * 10);
   echo "Logget out";
}


/* KÄYTTÄJÄN TUNNISTUS */
if(isset($_COOKIE['log_key'])){

   //HAETAAN KÄYTTÄJÄN TIEDOT
   $sql = "SELECT
   id,
   tunnus,
   DATE_FORMAT(last_load,'%d.%m.%y %h:%i:%s') AS last_load
   FROM {$tbl_users}
   WHERE istunto = '".mysql_real_escape_string($_COOKIE['log_key'])."'";
   $sql = mysql_query($sql,$lnk) or die(mysql_error());
   if($sql && mysql_num_rows($sql) == 1){
      $user = mysql_fetch_assoc($sql);
      mysql_query("UPDATE {$tbl_users} SET
      last_load = NOW()
      WHERE id = ".$user['id'], $lnk) or die(mysql_error());

   }


} //Jos ei ole taulua, luodaan se
mysql_query("CREATE TABLE IF NOT EXISTS `{$tbl_users}` (
  id int(11) NOT NULL auto_increment,
  tunnus varchar(50) default NULL,
  salasana varchar(32) default NULL,
  oikeanimi TEXT,
  email varchar(60) default NULL,
  ika INT,
  kotisivu TEXT,
  kuvaus TEXT,
  last_load timestamp(14) NOT NULL,
  istunto varchar(32) default NULL,
  PRIMARY KEY  (id),
  UNIQUE KEY istunto (istunto)
)",$lnk);

Nyt on noin. Tuossa käyttäjän tunnistus kohdassa uskoisin sen virheen olevan, mutta en tiedä mikä se on.

Triton [17.06.2009 15:33:02]

#

Minkätakia tallennat käyttäjän tiedot aina omaan tauluun? Eikö se mene niin, että taulujen määrä ei saa lisääntyä vaikka tiedon määrä kasvaa? Eli voisithan vain tehdä taulun nimeltä "kayttajat" ja yhdessä tietueessa olisi yhden käyttäjän tiedot. Samoin tuo istuntotunnisteen tallentaminen kantaa on minusta hieman turhaa eikö ihan vain istuntojen käyttö olisi parempi tapa... Ja sen käyttäjän tunnistuksen voisi tehdä vaikka näin:

<?php

		$sql = "SELECT * FROM kayttajat WHERE
				tunnus = '{$tunnus}' AND salasana = '{$salasana}'";

		$tulos = mysql_query($sql,$yhteys);

		if (mysql_fetch_assoc($tulos)) {
			echo "Sisällä ollaan!";
		}


?>

Tässähän yksinkertaisesti tehdään select-haku ja tarkistetaan löytyykö annetuilla tunnus-salasana-parilla yhtään riviä... Kannattaisi käyttää myös jotain suolaa salasanoissa ja itse käyttäisin myös SHA1-tiivistealgoritmia...

Teuro [17.06.2009 15:35:31]

#

Ei käyttäjän tietoja tallenneta omaan tauluun, vaan jokainen käyttäjä on oma tietueensa taulussa kayttajat. Minulla on siis itselläni juurikin sama scripti käytössä hieman muokattuna tosin.

MIB [17.06.2009 15:43:22]

#

Toni: Ei siellä ole jokaiselle omaa taulua. Myös tuo sinun tunnistuksesi on ihan sama tehtynä toisella tavalla kuin minun; Tuo palauttaa true/false mutta minun numeron 0/1.

Teuro, miten sinun eroaa tuosta koodivinkistä? =)

Muuntelin myös vähän, ihan kokeiluksi:

<?php
include("config.php"); //muuta config.php:n polku oikeaksi
//avataan yhteys tietokantaan
$lnk = mysql_connect($db_server,$db_user,$db_passwd) or die (mysql_error());
mysql_select_db($db_db,$lnk) or die (mysql_error());

//käyttäjä on oletuksena false. Älä varsinkaan poista, ellet tiedä mitä teet :)
$user = false;


/* SISÄÄNKIRJAUTUMINEN */
if(isset($_POST['tunnus']) && isset($_POST['salasana'])){

   //muuttujat turvallisesti talteen
   $tunnus = get_magic_quotes_gpc() ? $_POST['tunnus'] : mysql_real_escape_string($_POST['tunnus']);
   $salasana = get_magic_quotes_gpc() ? $_POST['salasana'] : mysql_real_escape_string($_POST['salasana']);
   $salasana = md5($salasana);

   //luodaan käyttäjäkohtainen uniikki id
   $istuntotunnus = md5(uniqid(""));
   //lisätään istunto tietokantaan käyttäjän tietoihin
   mysql_query("UPDATE {$tbl_users}
   SET istunto = '{$istuntotunnus}'
   WHERE tunnus = '{$tunnus}'
   AND salasana = '{$salasana}'",$lnk) or die (mysql_error());
   if(mysql_affected_rows($lnk) == 1){
      setcookie("log_key", "$istuntotunnus");
      echo "Katsotaan onko kirjauduttu (Päivitä, näkyykö cryptattu id?): " . $_COOKIE["log_key"] . "";
   }
}

/* ULOSKIRJAUTUMINEN */
if(isset($_REQUEST['logout'])){
	setcookie("log_key", "");
	setcookie("log_key", "", time() - 60 * 10);
    echo "Logget out<br />";
}

if(!isset($_COOKIE["log_key"])) {
	echo "Ei ole kirjauduttu<br />";
}


/* KÄYTTÄJÄN TUNNISTUS */
if(isset($_COOKIE['log_key'])){

   //HAETAAN KÄYTTÄJÄN TIEDOT
   $sql = "SELECT
   id,
   tunnus,
   DATE_FORMAT(last_load,'%d.%m.%y %h:%i:%s') AS last_load
   FROM {$tbl_users}
   WHERE istunto = '".mysql_real_escape_string($_COOKIE['log_key'])."'";
   $sql = mysql_query($sql,$lnk) or die(mysql_error());
   if($sql && mysql_num_rows($sql) == 1){
      $user = mysql_fetch_assoc($sql);
      mysql_query("UPDATE {$tbl_users} SET
      last_load = NOW()
      WHERE id = ".$user['id'], $lnk) or die(mysql_error());

   }


} //Jos ei ole taulua, luodaan se
mysql_query("CREATE TABLE IF NOT EXISTS `{$tbl_users}` (
  id int(11) NOT NULL auto_increment,
  tunnus varchar(50) default NULL,
  salasana varchar(32) default NULL,
  oikeanimi TEXT,
  email varchar(60) default NULL,
  ika INT,
  kotisivu TEXT,
  kuvaus TEXT,
  last_load timestamp(14) NOT NULL,
  istunto varchar(32) default NULL,
  PRIMARY KEY  (id),
  UNIQUE KEY istunto (istunto)
)",$lnk);

Siltikään ei toimi.

Triton [17.06.2009 15:53:35]

#

Miteköhän olet sitten tallentanut nuo tiedot? Ihmettelen edelleen sitä, että tuossa update-kyselyssä sinulla on taulun nimen paikalla muuttuja $tbl_users eli silloin tuo taulun nimi on vaihtuva? Samoin luot tuossa samaisessa koodissa uuden taulun uutta käyttäjää varten...

Teuro [17.06.2009 15:57:14]

#

Luepa tuo ajv:n vinkki läpi. require('config.php'); sisältää tietokannan asetukset, muun muassa käyttäjätaulun nimen ($tbl_user). Tuon viimeisen SQL lauseen voi toki poistaakin, ei se mitään uutta taulua luo, koska sellainen on jo olemassa. Lisäksi lauseessa todetaan explisiittisesti IF NOT EXISTS, joka siis tarkoittaa, että jos taulua ei ole olemassa.

MIB [17.06.2009 15:57:33]

#

Tutkis tuota ajv:n koodivinkkiä, niin tiedät mitä tuo $tbl_users tarkoittaa. Vilkaise sitä config.php:tä.

Edit: Teuro ehtikin ensiksi... Mutta, sitä ihan oikeaa ongelmaa jos edetään...

Triton [17.06.2009 15:59:49]

#

Teuro kirjoitti:

Luepa tuo ajv:n vinkki läpi. require('config.php'); sisältää tietokannan asetukset, muun muassa käyttäjätaulun nimen ($tbl_user). Tuon viimeisen SQL lauseen voi toki poistaakin, ei se mitään uutta taulua luo, koska sellainen on jo olemassa. Lisäksi lauseessa todetaan explisiittisesti IF NOT EXISTS, joka siis tarkoittaa, että jos taulua ei ole olemassa.

No siinä tapauksessa...

MIB [17.06.2009 16:04:24]

#

Joo, no palataankos ihan siihen ongelmaan?
Tiedättekö miksi ei toimi? :/ Minä en keksi ainakaan mitään syytä siihen.
Tuossa käyttäjän tunnistuksessa on se ongelma. Se ei saa tuohon $user tauluun tietoja...

TeNDoLLA [17.06.2009 18:18:05]

#

En nyt ole hetkeen seurannut tätä ketjua, mutta heitänpä tähän jotain kuitenkin jos tuota lähti debuggaamaan, niin kannattaa varmistaa:
1. Että mitä tuolla $_COOKIE['log_key']:ssa on sisältönä ennen tuon kyselyn tekemistä.
2. Katsoa löytyykö kannasta varmasti vastaava tieto.
3. Ajaa tuo sun kyselys suoraan jostain SQL clientistä ja katsoa mitä palautuu vai palautuuko mitään, jospa noilla pääsis jo jäljille missä ongelma piilee.

Luultavasti se ei mene tuon sun if -lauseen sisälle, koska se sun ehtos ei jostain syystä toteudu ja sen takia, user on edelleen false tuon kyselynkin jälkeen.

Voit myös kokeilla tuota sun iffin sisällä olevaa ehtoa var_dumpilla juuri ennen sitä if lausetta ja kattoa mitä siihen ehtoon tulee (true vai false)

<?php
var_dump($sql && mysql_num_rows($sql) == 1);
?>

MIB [17.06.2009 19:56:49]

#

Palauttaa "bool(false)" kun on tuossa kirjautumiskyselyn edessä, mutta siellä käyttäjätunnistuskohdassa kyselyn suorittamisen jälkeen/tai sen edessä ei palauta mitään.

Keksissä on sisältönä md5-hassattu "uniqid".

Sen verran sain tietoon, että virhe tulee siitä, että käyttäjän tunnistuksessa arvo on $sql:ssä 0 eli false. Tutkin mistä tulee...

Edit: Täällä Putkassahan pystyy määrittämään, kirjautuuko sessioneilla vai ei, niin heittääkö koodi tunnukset sitten keksiin ja niiden kanssa sitten kirjautuu?
Nyt tämä menee mielestäni vähän hankalaksi, kun ei tuo onnistu.
Ongelma on nähtävästi tuossa "istuntotunnuksessa".

MIB [18.06.2009 10:45:58]

#

Koodi stoppaa tähän kyselyyn:

<?php
   $sql = "SELECT
   id,
   tunnus,
   DATE_FORMAT(last_load,'%d.%m.%y %h:%i:%s') AS last_load
   FROM {$tbl_users}
   WHERE istunto = '".mysql_real_escape_string($_COOKIE['log_key'])."'";
?>

Kun sen laittaa näin

<?php
   $sql = "SELECT
   id,
   tunnus,
   DATE_FORMAT(last_load,'%d.%m.%y %h:%i:%s') AS last_load
   FROM {$tbl_users}
   WHERE tunnus = '$tunnus'
   AND salasana = '$salasana'";
?>

... Se kirjaa tunnuksen last_loadit sun muut, mutta tämä ei kuitenkaan toimi oikein.
Kun sivulta poistuu, tiedot nollaantuvat (Ei kannassa). Eli tulos on se, että log_keyn ja istunnon (kannassa) uniqid:t eivät ole samat.

MIB [21.06.2009 17:05:33]

#

Tuon keksijutun sain toimimaan, mutta viestin lähetyksessä on ongelmia.
Toisaalta olisi hyvä, että liian pitkiä viestejä ei kirjoitettaisi, mutta en haluaisi sen kuitenkaan tulostavan tätä errororia, "Got a packet bigger than 'max_allowed_packet' bytes".

Tiedän miten saan oman errorin tuon tilalle, mutta paljonkohan tuo max_allowed_packet on?
Laitoin kasan kirjaimia viestiin, ja teki tuon errorin.

mysql_query("SET @@session.max_allowed_packed=xxxxx");

Näin saa muutettua sitä?

trilog [21.06.2009 17:43:20]

#

MIB kirjoitti:

Tiedän miten saan oman errorin tuon tilalle, mutta paljonkohan tuo max_allowed_packet on?

Oletuksena palvelimen on 1MB ja asiaksohjelman 16MB.

MIB kirjoitti:

mysql_query("SET @@session.max_allowed_packed=xxxxx");

Näin saa muutettua sitä?

Pikaisen Googletuksen jälkeen, sitä ei nähdäkseni voi muuttaa lennosta.

http://dev.mysql.com/doc/refman/5.1/en/packet-too-large.html
http://www.vbulletin.com/forum/showpost.php?p­=621869&postcount=2

MIB [21.06.2009 19:39:05]

#

Okei, kiitos tiedosta.
Koitan asentaa tässä SMTP ohjelmaa Xamppliten seuraksi, vaikuttaa tosin aika toivottomalta. Tarkistankin, olisiko Xamppissa jo itsessään SMTP ohjelma...

MIB [22.06.2009 12:40:10]

#

Muuten, kun tein tuommoisen viestin muokkaussysteemin, niin haluaisin tehdä myös niin kuin täällä Putkassa, että tunnin sisällä vain voi muokata viestiään.
Jos aika olisi 1245663507 milloin viesti on lähetetty, niin voinko verrata aikaa niin, että lisää tuohon 3600, niin tuleeko siitä silloin oikea aika?
Luulisin, mutta en ole ihan perillä siitä mitkä kohdat tuosta sarjasta vastaa mitäkin yksikköä.

Edit: Ja kun aika on haettu kannasta tietyn viestin kohdalta, niin vertaus menee näin: (?)

<?php
$totalaika = $aikaa + 3600;
if ($totalaika > time()) {
//Näytetään muokkauslomake
}
?>

Mutta, kun tuossa on tuo If-lause, niin miten päin tuon merkin kuuluisi olla? :D
Nyt tökkii vähäsen, en muista miten sen kuuluisi olla...

Edit: Joo, näin se toimii ;)

Edit (Taas kerran):
Niin, vielä sellainen, että jos aiheeseen on vastattu ennen kuin muokkausaika on umpeutunut, niin ei pystyisi muokkaamaan viestiä.
Miten tämä kannattaisi tehdä? Viestit on ryhmitelty aihe_id:n mukaan.

Teuro [22.06.2009 12:59:09]

#

<?php
echo date("d.m.Y : H.i.s", 1245663507);
/* 22.06.2009 : 09.38.27 */
?>

Toiseen kysymykseen saat etsiä ratkaisun itse, mutta haluat siis lomakkeen näkyville, mikäli aikaa on kulunut lähetyksestä vähemmän kuin tunti? Silloin otat viestin lähetyksen yhteydessä tallennetun aikaleima, johon lisäät sopivasti aikaa, jonka jälkeen vertaat nykyistä aikaleimaa laskettuun aikaleimaan.

MIB [22.06.2009 13:01:11]

#

Sen sainkin tehtyä, mutta katsos tuo vika edit kohta. :D

Teuro [22.06.2009 13:12:46]

#

Katsot onko kyseisen henkilön viimeisin lähetetty viesti kyseisen langan viimeinen viesti.

<?php
    if($rivi['viesti_id'] !== $rivi['viimeisin']){
        /* Viestiin on vastattu */
    }else{
        /* Viestiin ei ole vastattu vielä */
    }
?>

MIB [22.06.2009 13:20:02]

#

Vai kannattaako minun laskea kaikki viestit siitä viestiketjusta ja sitten katsoa, että jos kyseisen viestin id on pienmpi kuin total määrä, niin on vastattu, muutoin näytetään taas se muokkauslomake?
Tämä olisi minusta helpompi toteuttaa, ainakin näen sen selvästi päässäni miten se menisi.

MIB [22.06.2009 13:26:23]

#

Eli Teuron esimerkin mukaan viesti_id olisi sen viestin numero (tuohon tulisi muuttuja), ja viimeisin olisi viestien yhteismäärä aiheessa?

Ei myöskään haittaa, että jos toiseen aiheeseen vastataan siinä välissä, tuo toimii silti?

Teuro [22.06.2009 14:34:04]

#

MIB kirjoitti:

Vai kannattaako minun laskea kaikki viestit siitä viestiketjusta ja sitten katsoa, että jos kyseisen viestin id on pienmpi kuin total määrä, niin on vastattu, muutoin näytetään taas se muokkauslomake?

Jos viesteillä on automaagisesti kasvava indeksointi, niin tuo malli ei toimi mitenkään, koska viimeistään toisessa langassa jokaisen viestin id on suurempi, kuin langassa olevien viestien määrä.

MIB kirjoitti:

Ei myöskään haittaa, että jos toiseen aiheeseen vastataan siinä välissä, tuo toimii silti?

Miten toinen lanka, jota ei edes käsitellä tässä kyselyssä voisi vaikuttaa tuohon?

MIB [22.06.2009 18:09:07]

#

Teuro kirjoitti:

Jos viesteillä on automaagisesti kasvava indeksointi, niin tuo malli ei toimi mitenkään, koska viimeistään toisessa langassa jokaisen viestin id on suurempi, kuin langassa olevien viestien määrä.

Okei, no heitetään tämä idea mereen.

Teuro kirjoitti:

Miten toinen lanka, jota ei edes käsitellä tässä kyselyssä voisi vaikuttaa tuohon?

Ajattelin vähän sekavasti. Kauppareissu auttoi tässä asiassa, nyt sain toimimaan tuon sinun esimerkin, vähän kantapään kautta :)

<?php
	$yhteys = mysql_connect("localhost", "root", "");
	mysql_select_db("forum");

	$id = $_GET["id"];
	$kysely = "SELECT * FROM viestit WHERE aihe_id = '".$_GET["aihe"]."' ORDER BY aika DESC LIMIT 1";
	$hae = mysql_query($kysely) or die(mysql_error());

	for ($i = 0; $i < mysql_num_rows($hae); $i++) {
		$vika = mysql_result($hae, $i, "viesti_id");

		if ($id !== $vika) {
			echo "Viestiin on vastattu";
		}else {
			echo "Viestiin ei ole vastattu";
		}
	}
	mysql_close($yhteys);
?>

Voisi sen varmaan helpomminkin tehdä.. :D Sanokaa vain, miten tuon voisi paremmin tehdä. Mielestäni tuo kyllä on 10 arvoinen siihen verrattuna, mitä osaan :D

MIB [23.06.2009 14:45:10]

#

Hei,

Olen nyt säätämässä profiilisivua tässänäin, mutta tuli yksi ongelma
Sivulla on ensin kaikenlaisia tietoja käyttäjästä, käytännössä samat kuin Putkassa noihin kuviin asti, johon ongelmani liittyykin.
Olen käyttänyt Antin koodivinkkiä apuna ympyrädiagrammiin, ja se pitäisi asettaa sivun alareunaan.
Ongelmana on se, että se sanoo "Headers already sent...", koska sivulla tulostetaan tavaraa ennen kuvaa. Miten saisin tämän kuvan sivun alareunaan?

Teuro [23.06.2009 14:55:04]

#

Mahdatko käyttää GD kirjastoa kuvan generointiin? Mikäli näin kannattaa itse kuvan piirto tehdä omassa tiedostossaan, jossa otsikot laitetaan heti tiedoston alussa kuntoon. Itse sivulla, jonne kuvan haluat voit laittaa ihan normaalin kuva tagin, jossa src kohta on kuvan generoivan tiedoston osoite.

<?php
/* kuva.php */
/* Antin GD-opas */
//lähetetään tunniste selaimelle
header("Content-type: image/png");

//luodaan 200x100-pikselin kokoinen kuva
$kuva=imagecreate(200,100);

//määritetään taustaväri ja kaksi muuta väriä
$tausta=imagecolorallocate($kuva, 255, 255, 255);
$musta=imagecolorallocate($kuva,0,0,0);
$sininen=imagecolorallocate($kuva,0,0,255);

//piirretään kehykset, teksti ja viiva
imagerectangle($kuva,0,0,199,99,$musta);
imagestring($kuva,2,10,10,"GD-kirjasto toimii!",$sininen);
imageline($kuva,10,24,130,80,$sininen);

//lähetetään kuva PNG-muodossa
imagepng($kuva);

//poistetaan kuva muistista
imagedestroy($kuva);
?>
<?php
/* profiili.php */

echo "<img src=\"kuva.php\" alt=\"viestien aluejakauma\" />";
?>

MIB [23.06.2009 15:01:20]

#

Empä tullut ajatelleeksi, että voi laittaa noin... :D Kiitos avusta.
Toisena olisi sellainen ongelma, että kun pitää hakea viestien määrä per käyttäjä per alue, niin tulee ongelmia.
Viestit taulussa ei viitata missään kohdin alueisiin. Viesteissä on aihe_id joka viittaa aiheeseen ja aihe taulussa on alue_id, joka viittaa alueeseen.

Tältä näyttää toivoton yritykseni:

<?php
//kuvan alustaminen
$leveys=400;$korkeus=230;
header ("Content-type: image/png");
$im = @ImageCreate ($leveys, $korkeus)
    or die ("GD-kirjaston käyttäminen ei onnistu!");
$valkoinen = ImageColorAllocate ($im, 255, 255, 255);
$musta=ImageColorAllocate ($im, 0, 0, 0);

$y = mysql_connect ("localhost", "root", "");
mysql_select_db("forum");

$haku = mysql_query("
SELECT
 v.viestit,
 a.alue
FROM
 alueet AS a
 LEFT JOIN viestit AS v
WHERE id = '".$_GET["id"]."'");
$nso = mysql_num_rows($haku);
$yk = "100";

//kuvaajan tiedot
$otsikko="Viestien aluejakautuma";
$arvo[0][0]=$nso;
$arvo[0][1]="Ns. ja -o";
$arvo[1][0]=$yk;
$arvo[1][1]="Yleinen k.";
$yksikko="";



//arvojen yhteismäärä ja värien määritys
for ($i=0;$i<count($arvo);$i++)
  {
  $yht=$yht+$arvo[$i][0];
  $arvo[$i][2]=ImageColorAllocate ($im, $i*60,($i+1)*60,($i+2)*60);
  }

//kehykset
ImageRectangle($im,1,1,$leveys-1,$korkeus-1,$musta);
ImageRectangle($im,$leveys-150,40,$leveys-10,
40+count($arvo)*(ImageFontHeight(2)+4),$musta);

//otsikko
$opituus=ImageFontWidth(5)*strlen($otsikko);
$okohta=$leveys/2-$opituus/2;
ImageString($im,5,$okohta,5,$otsikko,$musta);

//kuvion piirtäminen
$vkulma=0;
for ($i=0;$i<count($arvo);$i++)
  {
  ImageFilledRectangle($im,$leveys-145,43+$i*(ImageFontHeight(2)+4),
$leveys-138,50+$i*(ImageFontHeight(2)+4),$arvo[$i][2]);
  ImageString($im,2,$leveys-135,40+$i*(ImageFontHeight(2)+4),
$arvo[$i][1]." (".$arvo[$i][0].$yksikko.")",$musta);
  $kulma=($arvo[$i][0]/$yht)*360;
  ImageFilledArc($im,120,120,180,180,$vkulma,
$vkulma+$kulma,$arvo[$i][2],IMG_ARC_PIE);
  $vkulma=$kulma+$vkulma;
  }
ImageArc($im,120,120,180,180,0,360,$musta);

//kuva PNG-muotoon
ImagePNG ($im);
?>

Koitin myös kyselynä tälläistä:

SELECT
 v.id,
 ai.alue_id,
 al.id
FROM
 viestit AS v
 LEFT JOIN aiheet AS ai ON v.id=ai.lahettaja_id
 LEFT JOIN alueet AS al ON ai.alue_id=al.id
WHERE
 id = '".$_GET["id"]."'";

Mutta, miten minä tässä nyt sitten laskisin nuo arvot... :S

MIB [23.06.2009 20:34:57]

#

Teuro kirjoitti:

<?php
$a = 0;
while($rivi = mysql_fetch_array($tulos)){
    echo"<tr>";
    $vari = ($a % 2 == 0) ? 'punainen' : 'vihrea';
    echo"<td class=\"$vari\">".$rivi['otsikko']."</td>";
    $a++;
    echo"</tr>";
}

Ei niin kamalan hankalaa eihän?

Kokeilin tätä niin, että täytin kaikki kohdat oikein.
Laitoin vain classin tilalle bgcolor ja nuo värit kuntoon.
Se ei vain toiminut. :/ Kaikki meni siksi väriksi mikä on punaisen kohdalla.

<?php
require_once("yla.php");
require_once("ylaosa.php");

mysql_query("CREATE TABLE alueet(
id INT UNSIGNED AUTO_INCREMENT NOT NULL PRIMARY KEY, alue TEXT)");
$ky = "SELECT * FROM alueet";
$ha = mysql_query($ky) or die(mysql_error());


//Luodaksesi uuden aiheen, mene luoalue.php tiedostoon
echo '<table class="teksti" width="95%" cellspacing="0">';
echo "Keskustelu<br><br>";
echo '<tr class="taulukkoyla">
<td><b>Alue</b></td><td><b>Aiheita / Viestejä</b></td><td><b>Uusin viesti</b></td></tr>';
for ($i = 0; $i < mysql_num_rows($ha); $i++) {
$alue = mysql_result($ha, $i, "alue");
$id = mysql_result($ha, $i, "id");

$ky2 = "SELECT * FROM aiheet WHERE alue_id = '$id'";
$ha2 = mysql_query($ky2) or die(mysql_error());

$k = "SELECT * FROM viestit JOIN aiheet ON viestit.aihe_id=aiheet.id AND aiheet.alue_id='$id'";
$h = mysql_query($k) or die(mysql_error());

$a = mysql_num_rows($ha2);
$v = mysql_num_rows($h);
$k = "SELECT * FROM viestit JOIN aiheet ON viestit.aihe_id=aiheet.id AND aiheet.alue_id='$alue_id' ORDER BY viestit.aika DESC LIMIT 1";
$h = mysql_query($k) or die(mysql_error());

$hh = mysql_query("SELECT * FROM viestit WHERE alue = '$id' ORDER BY aika DESC LIMIT 1");

while ($rii = mysql_fetch_assoc($hh)) {
$ao = $rii["otsikko"];
$aol = $rii["aihe_id"];
$aa = date("d.m.Y H:i:s", $rii["aika"]);
$al = $rii["lahettaja_id"];
$aal = $rii["alue"];
$ali = $rii["id"];
}

$a = 0;
while($rivi = mysql_fetch_array($ha)){
$vari = ($a % 2 == 0) ? 'EAEAEA' : 'FFFFFF';


$vikaviesti = "<a href=\"alue.php?aiheid=$aol&alue=$aal\">$ao</a><br>$aa<br><a href=\"profiili.php?id=$ali\">$al</a>";
echo "<tr bgcolor=\"$vari\"><td><a href=\"alueet.php?alue=$id\">$alue</a></td>
<td>$a / $v</td><td><br>$vikaviesti<br></td></tr>";
$a++;
}
}
echo "</table>";

require_once("alaosa.php");
?>

Kaikki muu toimii oikein.

Tumettaja [23.06.2009 21:49:38]

#

$vari = ($a % 2 == 0) ? 'EAEAEA' : 'FFFFFF';

=>

$vari = ($a % 2 == 0) ? '#EAEAEA' : '#FFFFFF';

:)

MIB [23.06.2009 21:55:09]

#

Ei se siitä kyllä johdu. Ongelma on se, että se tulostaa vain ensimmäisen alueen.

Teuro [24.06.2009 12:21:50]

#

Mitä tulee tulostukseen seuraavalla koodilla?

<?php
/* Laita tähän tietokannan asetukset */

$alueet = mysql_query("SELECT alue, id FROM alueet ORDER BY id");

while($rivi = mysql_fetch_array($alueet)){
    echo "Alue = " . $rivi['alue'] . " id = " . $rivi['id'] . "<br />";
}
?>

Tulee tulostukseen kaikki alueet ja niiden id numerot? Mikäli ei tule tarkista tietokannan alueet taulu huolellisesti läpi, että siellä ei ole mitään virheitä. Sitten aja seuraava koodinpätkä läpi. Tässä on muutoin sama kysely, mutta jokaisen alueen alapuolelle pitäisi tulostua alueella olevat viestit.

<?php
/* Laita tähän tietokannan asetukset */

$alueet = mysql_query("
SELECT
  alue,
  id
FROM
  alueet
ORDER BY
  id");

while($rivi = mysql_fetch_array($alueet)){
    echo "Alue = " . $rivi['alue'] . " id = ".$rivi['id']."<br />";
    $viestit = mysql_query("
SELECT
  otsikko
FROM
  viestit,
  aiheet
WHERE
  viestit.id = $rivi['id']");

    while($tiedot = mysql_fecth_array($viesit)){
      echo $tiedot['otsikko'] . "<br />";
    }
}
?>

Mikäli ei hirmuisia typoja tullut, niin noiden kahden koodipätkän pitäisi tulostaa kaikki kannassa olevat alueet ja niiden alle otsikot.

MIB [24.06.2009 12:38:49]

#

Taulussa ei ole mitään ongelmia, kaikki on pilkun tarkalleen oikein.
Tuo ensimmäinen koodisi toimii (Tulostaa alueet 1 ja 2 + nimet), mutta tuo toinen tulostaa alueet 1 2 ja uudelleen 1. Alueita onkin yhteensä 2.

Se toimii myös näin:

<?php
$y = mysql_connect("localhost", "root", "");
mysql_select_db("forum");

$alueet = mysql_query("SELECT alue, id FROM alueet ORDER BY id");

$a = 0;
echo "<table>";
while($rivi = mysql_fetch_array($alueet)){
$vari = ($a % 2 == 0) ? '#EAEAEA' : '#FFFFFF';
    echo "<tr bgcolor=\"$vari\"><td>Alue = " . $rivi['alue'] . " id = " . $rivi['id'] . "</td></tr>";
$a++;
}
echo "</table>";
mysql_close($y);
?>

.. joka on hyvä asia. Mutta tuon kun laittaa for silmukan sisään, niin eipä enään toimikkaan: Kaikki tulostuvat kahdesti:

<?php
require_once("yla.php");
require_once("ylaosa.php");

$ky = "SELECT * FROM alueet";
$ha = mysql_query($ky) or die(mysql_error());


//Luodaksesi uuden aiheen, mene luoalue.php tiedostoon
echo '<table class="teksti" width="95%" cellspacing="0">';
echo "Keskustelu<br><br>";
echo '<tr class="taulukkoyla">
<td><b>Alue</b></td><td><b>Aiheita / Viestejä</b></td><td><b>Uusin viesti</b></td></tr>';
for ($i = 0; $i < mysql_num_rows($ha); $i++) {
$alue = mysql_result($ha, $i, "alue");
$id = mysql_result($ha, $i, "id");

$ky2 = "SELECT * FROM aiheet WHERE alue_id = '$id'";
$ha2 = mysql_query($ky2) or die(mysql_error());

$k = "SELECT * FROM viestit JOIN aiheet ON viestit.aihe_id=aiheet.id AND aiheet.alue_id='$id'";
$h = mysql_query($k) or die(mysql_error());

$a = mysql_num_rows($ha2);
$v = mysql_num_rows($h);
$k = "SELECT * FROM viestit JOIN aiheet ON viestit.aihe_id=aiheet.id AND aiheet.alue_id='$alue_id' ORDER BY viestit.aika DESC LIMIT 1";
$h = mysql_query($k) or die(mysql_error());

$hh = mysql_query("SELECT * FROM viestit WHERE alue = '$id' ORDER BY aika DESC LIMIT 1");

while ($rii = mysql_fetch_assoc($hh)) {
$ao = $rii["otsikko"];
$aol = $rii["aihe_id"];
$aa = date("d.m.Y H:i:s", $rii["aika"]);
$al = $rii["lahettaja_id"];
$aal = $rii["alue"];
$ali = $rii["id"];
}
/*
$a = mysql_num_rows($ha);
while($rivi = mysql_fetch_assoc($ha)){
    $vari = ($a % 2 == 0) ? '#EAEAEA' : '#FFFFFF';
    $a++;
}


$vikaviesti = "<a href=\"alue.php?aiheid=$aol&alue=$aal\">$ao</a><br>$aa<br><a href=\"profiili.php?id=$ali\">$al</a>";
echo "<tr bgcolor=\"$vari\"><td><a href=\"alueet.php?alue=$id\">$alue</a></td>
<td>$a / $v</td><td><br>$vikaviesti</td></tr>";
}*/

$alueet = mysql_query("SELECT alue, id FROM alueet ORDER BY id");

$a = 0;

while($rivi = mysql_fetch_array($alueet)){
$vari = ($a % 2 == 0) ? '#EAEAEA' : '#FFFFFF';
    $vikaviesti = "<a href=\"alue.php?aiheid=$aol&alue=$aal\">$ao</a><br>$aa<br><a href=\"profiili.php?id=$ali\">$al</a>";
	echo "<tr bgcolor=\"$vari\"><td><a href=\"alueet.php?alue=$id\">$alue</a></td>
	<td>$a / $v</td><td><br>$vikaviesti</td></tr>";
$a++;
}
}
echo "</table>";
require_once("alaosa.php");
?>

Kaikki toimii, kuten pitääkin kun koodi on näin: (Miinus siitä noi värit sitten...)

<?php
require_once("yla.php");
require_once("ylaosa.php");

$ky = "SELECT * FROM alueet";
$ha = mysql_query($ky) or die(mysql_error());


//Luodaksesi uuden aiheen, mene luoalue.php tiedostoon
echo '<table class="teksti" width="95%" cellspacing="0">';
echo "Keskustelu<br><br>";
echo '<tr class="taulukkoyla">
<td><b>Alue</b></td><td><b>Aiheita / Viestejä</b></td><td><b>Uusin viesti</b></td></tr>';
for ($i = 0; $i < mysql_num_rows($ha); $i++) {
$alue = mysql_result($ha, $i, "alue");
$id = mysql_result($ha, $i, "id");

$ky2 = "SELECT * FROM aiheet WHERE alue_id = '$id'";
$ha2 = mysql_query($ky2) or die(mysql_error());

$k = "SELECT * FROM viestit JOIN aiheet ON viestit.aihe_id=aiheet.id AND aiheet.alue_id='$id'";
$h = mysql_query($k) or die(mysql_error());

$a = mysql_num_rows($ha2);
$v = mysql_num_rows($h);
$k = "SELECT * FROM viestit JOIN aiheet ON viestit.aihe_id=aiheet.id AND aiheet.alue_id='$alue_id' ORDER BY viestit.aika DESC LIMIT 1";
$h = mysql_query($k) or die(mysql_error());

$hh = mysql_query("SELECT * FROM viestit WHERE alue = '$id' ORDER BY aika DESC LIMIT 1");

while ($rii = mysql_fetch_assoc($hh)) {
$ao = $rii["otsikko"];
$aol = $rii["aihe_id"];
$aa = date("d.m.Y H:i:s", $rii["aika"]);
$al = $rii["lahettaja_id"];
$aal = $rii["alue"];
$ali = $rii["id"];
}

$vikaviesti = "<a href=\"alue.php?aiheid=$aol&alue=$aal\">$ao</a><br>$aa<br><a href=\"profiili.php?id=$ali\">$al</a>";
echo "<tr bgcolor=\"$vari\"><td><a href=\"alueet.php?alue=$id\">$alue</a></td>
<td>$a / $v</td><td><br>$vikaviesti</td></tr>";
}
echo "</table>";

require_once("alaosa.php");
?>

Teuro [24.06.2009 12:47:23]

#

Alemmassa while silmukassa oli typo siellä luki $rivi, vaikka piti lukea $tiedot. Kokeilepa nyt uudelleen tuota. Lisäksi kannattaa jättää kaikkia ulkopuolinen tauhka pois ja keskittyä saamaan oikeat tulokset esiin. Lopuksi vielä sellainen kommentti, että nimeä muuttujat paremmin ja laita kyselyyn vain ne kentät, joita aiot käyttää jatkossa.

Ei siis kannata hakea kaikkia kenttiä kannasta, mikäli käyttää vain kahta niistä. Lisäksi samlla voi kyselyssä muotoilla esimerkiksi päivämäärät oikeaan muotoon jo valmiiksi.

MIB [24.06.2009 12:57:47]

#

Teuro kirjoitti:

Lopuksi vielä sellainen kommentti, että nimeä muuttujat paremmin ja laita kyselyyn vain ne kentät, joita aiot käyttää jatkossa.

:D Hehe. Ne ovat kyllä kaikki lyhenteitä siitä mitä ne tekevät. Arvasin, että joku vielä sanoo siitä. :D

Joo, tajusin kyllä korjata tuon itse kuin luin sitä, mutta se tekee silti erroria. Tuloksena on:

Alue = alue1 id = 1

Warning: mysql_fetch_array(): supplied argument is not a valid MySQL result resource in C:\xampplite\htdocs\foorumi\testii.php on line 26
Alue = alue2 id = 2

Warning: mysql_fetch_array(): supplied argument is not a valid MySQL result resource in C:\xampplite\htdocs\foorumi\testii.php on line 26

Kun koodista oli virheet korjattuna:

<?php
$y = mysql_connect("localhost", "root", "");
mysql_select_db("forum");


$alueet = mysql_query("
SELECT
  alue,
  id
FROM
  alueet
ORDER BY
  id");

while($rivi = mysql_fetch_array($alueet)){
    echo "Alue = " . $rivi['alue'] . " id = ".$rivi['id']."<br />";
    $viestit = mysql_query("
SELECT
  otsikko
FROM
  viestit,
  aiheet
WHERE
  viestit.id = '".$rivi['id']."'");

    while($tiedot = mysql_fetch_array($viesit)){
      echo $tiedot['otsikko'] . "<br />";
    }
}

mysql_close($y);
?>

Metabolix [24.06.2009 13:03:19]

#

Vieläkään et ole oppinut jo satoja viestejä sitten neuvottua asiaa: tarkista kyselyiden virheet ja tulosta mysql_error()-funktion palauttama ilmoitus.

MIB [24.06.2009 13:09:08]

#

Kyllä ne on katsottu.
Se sanoo "Column 'otsikko' in field list is ambiguous" (Jäi mainitsematta viime viestistä). Ongelma ei poistu vaikka tuota kyselyä muokkaisin niin, että hakee vain yhdestä taulusta..

Teuro [24.06.2009 13:12:43]

#

MIB kirjoitti:

Kyllä ne on katsottu.
Se sanoo "Column 'otsikko' in field list is ambiguous" (Jäi mainitsematta viime viestistä). Ongelma ei poistu vaikka tuota kyselyä muokkaisin niin, että hakee vain yhdestä taulusta..

Ihan varmasti poistuu tuo kyseinen virhe, jos haet vain yhdestä taulusta, koska tuo error kertoo, että haettu kenttä ei ole yksiselitteinen. Samassa taulussa ei siis voi olla kahta identtistä kenttää, joten tuota virhettä ei voi tulla haettaessa yhdestä taulusta tietoa.

MIB [24.06.2009 13:18:23]

#

Anteeksi, mun moka.
Siis, se poistuu, mutta nuo muut mitä tuossa mainitsin ylempänä eivät poistu.
Ongelma on tuossa toisessa WHILE silmukassa ilmoitusten mukaan.
Nyt tämän pitäisi olla kaikkien osien oikein:

<?php
$y = mysql_connect("localhost", "root", "");
mysql_select_db("forum");


$alueet = mysql_query("
SELECT
  alue,
  id
FROM
  alueet
ORDER BY
  id") or die(mysql_error());

while($rivi = mysql_fetch_array($alueet)){
    echo "Alue = " . $rivi['alue'] . " id = ".$rivi['id']."<br />";
    $viestit = mysql_query("
SELECT
  otsikko
FROM
  viestit
WHERE
  alue = '".$rivi['id']."'") or die(mysql_error());

    while($tiedot = mysql_fetch_array($viesit)){
      echo $tiedot['otsikko'] . "<br />";
    }
}

mysql_close($y);
?>

Teuro [24.06.2009 14:10:31]

#

No kyselyssä numeraalien ympärille ei kuulu laittaa hipsuja, muuten tuo näyttää ihan oikealta.

Jotenkin musta alkaa tuntumaan siltä, että yrität samaan aikaan rakentaa kamalan montaa asiaa. Se eittämättä sekoittaa monelta osin ajattelua, joten voisin jopa suositella, että seuraavaksi suunnittelet ja rajaat ongelman osiksi, jonka jälkeen ratkot ongelmat yksi kerrallaan.

MIB [24.06.2009 14:38:30]

#

Nyt ei kyllä onnistu. :/
Lähin, mitä saan aikaan, näyttää tältä:

ALUE:     AIHETA / VIESTEJÄ:     VIIMEISIN:
Alue1     Aiheta / Viestejä      Viimeisin
Alue1     Aiheta / Viestejä      Viimeisin
Alue2     Aiheta / Viestejä      Viimeisin
Alue2     Aiheta / Viestejä      Viimeisin

Jossa aiheta ja viestejä arvot ovat ihan päin kuusta.

TeNDoLLA [24.06.2009 16:49:36]

#

Sulla on typo tuolla toisessa while silmukassa, $viesit --> $viestit.

MIB [24.06.2009 19:00:55]

#

TeNDoLLA kirjoitti:

Sulla on typo tuolla toisessa while silmukassa, $viesit --> $viestit.

Onneksi täällä on tarkkasilmäisiä :) No, kyllähän se nyt toimii, paitsi sitä taustaväri juttua en saa millä toimimaan. :( Osaisitko auttaa tässäkin? :D

TeNDoLLA [24.06.2009 19:57:03]

#

Pistäppä se koodin pätkä vielä kertaalleen missä se värin tulostus tapahtuu ja millanen seon tällä hetkellä. Miks sulla muuten on <br> tuolla tulostuksessa yhden <tr> tagin sisällä?

MIB [24.06.2009 20:33:51]

#

<?php
require_once("yla.php");
require_once("ylaosa.php");

$ky = "SELECT * FROM alueet";
$ha = mysql_query($ky) or die(mysql_error());


//Luodaksesi uuden aiheen, mene luoalue.php tiedostoon
echo '<table class="teksti" width="95%" cellspacing="0">';
echo "Keskustelu<br><br>";
echo '<tr class="taulukkoyla">
<td><b>Alue</b></td><td><b>Aiheita / Viestejä</b></td><td><b>Uusin viesti</b></td></tr>';
for ($i = 0; $i < mysql_num_rows($ha); $i++) {
$alue = mysql_result($ha, $i, "alue");
$id = mysql_result($ha, $i, "id");

$ky2 = "SELECT * FROM aiheet WHERE alue_id = '$id'";
$ha2 = mysql_query($ky2) or die(mysql_error());

$k = "SELECT * FROM viestit JOIN aiheet ON viestit.aihe_id=aiheet.id AND aiheet.alue_id='$id'";
$h = mysql_query($k) or die(mysql_error());

$a = mysql_num_rows($ha2);
$v = mysql_num_rows($h);
$k = "SELECT * FROM viestit JOIN aiheet ON viestit.aihe_id=aiheet.id AND aiheet.alue_id='$alue_id' ORDER BY viestit.aika DESC LIMIT 1";
$h = mysql_query($k) or die(mysql_error());

$hh = mysql_query("SELECT * FROM viestit WHERE alue = '$id' ORDER BY aika DESC LIMIT 1");

while ($rii = mysql_fetch_assoc($hh)) {
$ao = $rii["otsikko"];
$aol = $rii["aihe_id"];
$aa = date("d.m.Y H:i:s", $rii["aika"]);
$al = $rii["lahettaja_id"];
$aal = $rii["alue"];
$ali = $rii["id"];
}
$vikaviesti = "<a href=\"alue.php?aiheid=$aol&alue=$aal\">$ao</a><br>$aa<br><a href=\"profiili.php?id=$ali\">$al</a>";
$a = 0;
while($rivi = mysql_fetch_array($ha)){
$vari = ($a % 2 == 0) ? '#EAEAEA' : '#FFFFFF';
echo "<tr bgcolor=\"$vari\">";
echo "<td ><a href=\"alueet.php?alue=$id\">$alue</a></td>
<td>$a / $v</td><td><br>$vikaviesti</td>";
$a++;
echo "</tr>";
}
}
echo "</table>";

require_once("alaosa.php");
?>

Tämä näyttää kaiken ihan päin kuusta. Näkyy vain yksi alue (missä id 1) ja siinä on viestit ja aiheet ihan väärin (Siis, tuossa aihetta / viesiä kohdassa).

MIB [25.06.2009 13:56:28]

#

Jesh, sain tuon toimimaan. :)

Sellainen juttu vielä, että jos haluaisin linkeiksi myös http:// alkuiset, mutta en niitä joissa on pelkkä http://, niin miten tämä pitäisi tehdä? :/
Tällä hetkellä olen näin koittanut:

<?php
function varitaPHP($s) {
    return '<div style="border-style:solid;border-width:1px;background:white">'.
           highlight_string(html_entity_decode(stripslashes($s)), True).
           '</div>';
}

function bbcode_format($var) {
    $search = array(
		'/\http://(.*?)/is',
	    '/\[b\](.*?)\[\/b\]/is',
        '/\[i\](.*?)\[\/i\]/is',
        '/\[u\](.*?)\[\/u\]/is',
        '/\[url\](.*?)\[\/url\]/is',
        '/\[url\=(.*?)\](.*?)\[\/url\]/is',
        '/\[lainaus\](.*?)/is',
        '/\[lainaus "(.*?)"\](.*?)/is',
        '/\[\/lainaus\]/is',
        '/\[koodiphp\](.*?)\[\/koodiphp\]/ise'
        );
    $replace = array(
		'<a href="$1">$1</a>',
		'<strong>$1</strong>',
        '<em>$1</em>',
        '<u>$1</u>',
        '<a href="$1">$1</a>',
        '<a href="$1">$2</a>',
        '<i><small>$1 kirjoitti:</small></i><br><div style="border-style:solid;border-width:1px;background:#E4E9FF;margin-left:8px">$2<br></div>',
        '<i><small><br>$1 kirjoitti:</small></i><br><div style="border-style:solid;border-width:1px;background:#E4E9FF;margin-left:8px">$2',
        '<br></div>',
        "varitaPHP('\\1')"
        );
    $var = preg_replace($search, $replace, $var);
    return $var;
}
?>

trilog [25.06.2009 14:50:58]

#

MIB kirjoitti:

Sellainen juttu vielä, että jos haluaisin linkeiksi myös http:// alkuiset, mutta en niitä joissa on pelkkä http://, niin miten tämä pitäisi tehdä? :/

$search = array(
'/\http://(.*?)/is',

=>

$search = array(
'/(http:\/\/.+?)$/is',

MIB [25.06.2009 15:20:05]

#

Kiitos tuosta, vaikka jouduinkin ottamaan se pois. :/ Koko viesti menee linkiksi, kun tuolla ei ole lopetustagia.

trilog [25.06.2009 15:24:13]

#

Ohho, aivan, pahoitteluni. Yksi vaihtoehto on korvata tuo .+? => [^ ]+, jolloin se matchaa välilöyntiin asti. Tai sitten Internetistä etsii jonkun regexp:n linkkien parsintaan.

EDIT:
Löysin tällaisen regexp:n:

<?php
$search = '/((((https?|ftp):\/\/)|www\.)(([0-9]+\.[0-9]+\.[0-9]+\.[0-9]+)|localhost|([a-zA-Z0-9\-]+\.)*[a-zA-Z0-9\-]+\.(com|net|org|info|biz|gov|name|edu|coop|[a-zA-Z][a-zA-Z]))(:[0-9]+)?((\/|\?)[^ "]*[^ ,;\.:">)])?)+?/is';

$replace = '<a href="\\1">\\1</a>';

echo preg_replace($search, $replace, 'http://www.google.com/, hyvä hakukone');

MIB [25.06.2009 15:31:42]

#

Nyt tämä ei tee yhtikäs mitään. :o

MIB [26.06.2009 12:29:54]

#

Empäs huomannutkaan tuota koodinpätkää. :) Kyllä se toimii, kiitos siitä.
Kohta laitan demon nettiin.

MIB [26.06.2009 15:40:32]

#

Foorumi on nyt valmiina osoitteessa http://kamuweb.jouluserver.com/foorumi/
Ulkoasua en jaksanut vääntää, niin käytän yksinkertaistettua versiota Putkan ulkoasusta, jos se kelpaa Antille?

Jos kirjoittaisitte bugit sinne yleisen keskustelun alueelle, jos niitä ilmenee. :D

MIB [07.07.2009 12:43:57]

#

Uhhuh, ei tekisi mieli postata näin montaa viestiä peräkkäin, mutta jos muokkaan tuota, niin ei se sieltä ylös nouse ja kukaan ei huomaa mitään, joten pakko tehdä näinkin kivulias toimenpide.

Asiaan:
Tein tässä asennusohjelmaa tähän foorumiin, missä täytetään kaikki MySQL tiedot ja luodaan taulut sun muut.
Ongelmana on se, että miten tallennan nämä MySQL tiedot, eli MySQL serveri, tietokannan nimi, käyttäjätunnus ja salasana? Tietokantaan niitä ei tietenkään voi tallentaa.
Yhtenä ajatuksena tuli tekstitiedosto mieleen, mutta eikös tämä ole vähän turvatonta vaikka salasana olisi kryptattu?

Kysymys: Miten sinä sen tekisit?

Cornix [15.07.2009 00:57:24]

#

Useissa PHP-skripteissä salasanat ovat selkokielisinä skriptin seassa. Tallenna ihan PHP-tiedostona, jonka voit includettaa suoraan skriptissäsi?

Turvallisintahan tietysti olisi tallentaa tiedosto vielä jonnekkin www document rootin ulkopuolelle, mistä sitä ei varmasti serveri maailmalle tarjoilisi, mutta mitenpä tuollaisen polun, johon PHP:tä ajavalla käyttäjätunnuksella olisi kirjoitusoikeus, tietäisi varmasti?

Vastaukseni kysymykseen miten itse tekisit olisi siis, että tallentaisin PHP-skriptinä.

Jos et tallenna suoraan $muuttuja = "arvo"; -tyyliin, muista, että PHP-tulkki voi valittaa virheellisistä riveistä ja paljastaa ne selkokielisinä selaimen suuntaan. Siis joko kommenttimerkkien /* */ väliin tai validina PHP:nä.

tsuriga [15.07.2009 01:58:12]

#

Asetustiedostona (.ini, .yaml, jne.) www-rootin ulkopuolelle. Asennuksessa sitten tiedustellaan tuota asetustiedoston polkua jossei automaagisesti löydetä sopivaa hakemistoa.

Cornix [16.07.2009 15:11:45]

#

tsuriga kirjoitti:

Asennuksessa sitten tiedustellaan tuota asetustiedoston polkua jossei automaagisesti löydetä sopivaa hakemistoa.

Ai niin, ajattelin että tuota hakemistotietoa ei voisi tallentaa mihinkään, mutta hyvinhän sen voi tallentaa normaaliin tekstitiedostoon www-rootin allekin, kun kukaan ei selaimella voisi sitä itse salasanatiedostoa kuitenkaan onkia esille, vaikka sen hakemistopolun tietäisikin.

Tuo on kyllä turvallisempi tapa. :)


Sivun alkuun

Vastaus

Aihe on jo aika vanha, joten et voi enää vastata siihen.

Tietoa sivustosta