Avatar billede monkeysee Nybegynder
24. maj 2004 - 03:21 Der er 20 kommentarer og
1 løsning

Jeg vil lære PHP, og her er grunden til det

Hej PHP/eksperter!

Jeg har et ASP script som virker fint på IIS, og bruger FSO (file system object) til at læse filer af typen ".htm" i en bestemt folder, og sorterer og viser links til disse .htm filer via ADODB (connection-less recordsets).

Når jeg uploader dette script til en unix-baseret maskine (som kører Sun ASP) går alle mulige ting galt! For det første, så er FSO understøttelsen fuldstændig udokumenteret, så man skal forsøge sig frem, og for det andet mangler standard kommandoer som .Append i Sun's implementering af ADODB!!

Så jeg har besluttet at lære PHP, men har selvfølgelig brug for inspiration til at komme i gang (og har ikke tænkt mig at tage en måned fri for at læse en tyk bog - det bliver nødt til at vente til sommerferien;-).

Derfor har jeg lagt funktionerne i min asp/vbscript løsning op i sin fulde længde, og håber at en flink person kan vise mig hvilke kommandoer jeg bedst kan anvende for at lave en lignende funktionalitet, blot i PHP (og som en gulerod giver jeg 250 point, selvom det jo nærmest burde være kr,-)

Jeg har tilføjet en del kommentarer (på engelsk!) - forhåbentlig er det tydeligt hvad der foregår. Ellers spørg, så jeg kan forsøge at uddybe nærmere...

Here goes!
---------------------------------------------------
<%
' Return a list of the files in the named directory
' (strFolder) that match the given file extension (strExt)
'
Function getDirContents(strFolder,strExt)

    Dim fso,oRs,file,outputStr,folderObject,filesObject,tmpPgTitle,tmpModif

    Set fso = CreateObject("Scripting.FileSystemObject")
    Set folderObject = fso.GetFolder(Server.MapPath(strFolder))
    Set filesObject = folderObject.Files

    'Use the recordset object to emulate a table.
    Set oRs = CreateObject("ADODB.Recordset")
        oRs.Fields.Append "ID", 3
        oRs.Fields.Append "Name", 200, 100
        oRs.Fields.Append "LastModified", 133
        oRs.Open

    ' Create the entries in the recordset
    For Each file In filesObject

        ' Only add files with an allowed extension
        If fso.GetExtensionName(Server.Mappath(file.Name)) = strExt Then

            ' Prepare for new item
            oRs.AddNew
           
            ' Fill in each field
            oRs.Fields("Name").Value = file.Name
            oRs.Fields("LastModified").Value = file.DateLastModified
           
            ' Add the item to the recordset
            oRs.Update
        End If
    Next

    ' Now we can release the file system object from memory
    Set filesObject = Nothing
    Set folderObject = Nothing
    Set fso = Nothing

    ' Use the ADODB to sort the recordset
    oRs.Sort = "LastModified DESC"

    ' Set cursor to the beginning of our recordset
    If Not oRs.BOF Then
        oRs.MoveFirst
    End If

    ' Loop through the recordset
    While not oRS.EOF


        ' Display just the date, not date+time format. Achived by
        ' including just the first 10 characters of "LastModified"
        tmpModif = Left(oRs.Fields("LastModified").Value,10)

        ' Get the <title> attribute if present. Otherwise, use the filename
        tmpPgTitle = extractTitleAttr(getFileContents(strFolder & oRs.Fields("Name").Value)) & ""
        If tmpPgTitle = "" Then
            tmpPgTitle = oRs.Fields("Name").Value
        End If

        ' HTML to output
        outputStr = outputStr + "<a href=""default.asp?url=" & strFolder & oRs.Fields("Name").Value & """><span class=""smaller"">" & tmpModif & "</span><br>" & tmpPgTitle & "</a><hr>"
        oRs.MoveNext

    Wend

    getDirContents = outputStr

    Set oRs = Nothing

End Function


' Extract the <title> attribute of a string
' using regular expressions
Function extractTitleAttr(strng)

    Dim regEx, Match, Matches, outputStr

    Set regEx = New RegExp 
    regEx.Pattern = "(\<TITLE\>)(\s*)(.+)(\s*)(\<\/TITLE\>)"
    regEx.IgnoreCase = True 
    Set Matches = regEx.Execute(strng)

    ' Iterate Matches collection
    For Each Match in Matches 
        ' Extract the 3rd submatch (the title)
        Set Match = Matches(0)
        extractTitleAttr = Match.SubMatches(2)
    Next

    Set regEx = Nothing
    Set Match = Nothing
    Set Matches = Nothing
    Set outputStr = Nothing

End Function


' Return the contents of a file as a string
'
Function getFileContents(strHTMLFile)

    Dim fso,objText
   
    ' Establish a connection to the FSO (FileSystemObject)
    Set fso = Server.CreateObject("Scripting.FileSystemObject")
   
    ' If the file passed as argument exist
    If fso.FileExists(Server.MapPath(strHTMLFile)) Then
        ' Read the contents of the file
        Set objText = fso.OpenTextFile(Server.MapPath(strHTMLFile))
        getFileContents = objText.ReadAll
        objText.Close
        Set objText = Nothing
    Else
        ' File does not exist - output message
        getFileContents = "Der opstod en fejl - prøv evt. et andet link"
    End If
    Set fso = Nothing
End Function

%>
Avatar billede monkeysee Nybegynder
24. maj 2004 - 03:22 #1
Øhh..det skulle være 250 point, men max. her på eksperten er vist 200.

Venter spændt!

/danoise
Avatar billede technodance.dk Nybegynder
24. maj 2004 - 05:08 #2
er på msn :o)
Avatar billede monkeysee Nybegynder
24. maj 2004 - 07:25 #3
Hej technodance - jeg har desværre ingen messenger. Kan vi ikke klare diskussionen her på eksperten?
Avatar billede technodance.dk Nybegynder
24. maj 2004 - 07:29 #4
nej tak ikke i dette tilfel. ellers må vi maile
Avatar billede technodance.dk Nybegynder
24. maj 2004 - 07:49 #5
vil du svare???
Avatar billede Syska Mester
24. maj 2004 - 08:47 #6
han skal vel lige have tid til at svare.... du kan vel vente lidt....
Avatar billede sukos Juniormester
24. maj 2004 - 08:54 #7
hmm, du vil læse et dir igennem for html filer, og vise et link til hver fil, og hvis der er <title>Titel</title> så vise den ved siden af linket?
Og er der klikket på en fil, så vil du vise indholdet af filen?

Altsammen i samme script?
Avatar billede sostack Nybegynder
24. maj 2004 - 09:45 #8
<?php
$diret = "."; //Den mappe du vil liste filerne fra, det eneste der skal rettes.
$handle = opendir($diret);
WHILE(false !==($file = readdir($handle)))
{
    if("." != $file && ".." != $file && (".htm" == substr($file, -4) || ".html" == substr($file, -5)))
    {
        $udskrives = "<a href='$diret/$file'>";
        $fh = fopen($file, "r");
        $indhold = fread($fh, 256);
        $titel1 = explode("</title>", $indhold);
        $titel = explode("<title>", $titel1[0]);
        $udskrives .= $titel[1] . "</a><br />";
        echo $udskrives;
    }
}
?>

//sostack
Avatar billede monkeysee Nybegynder
24. maj 2004 - 11:42 #9
Hej Sostack! Jeg henter Apache + PHP og installerer det på min arbejds-PC, så jeg kan teste eksemplet. Men er det skrevet specifikt til unix/pc, eller "cross-platform" ? Jeg spørger, da jeg ikke kan se det udfra koden. Og jeg kan sagtens installere på en unix maskine hvis det er tilfældet!
Avatar billede monkeysee Nybegynder
24. maj 2004 - 11:47 #10
Og Sukos - du har forstået scriptet helt korrekt - blot sker der det, når man klikker på et link, at "default.asp" (som jo nok kommer til at hedde noget andet - hehe) sørger for at inkludere filen som er nævnt i forespørgelsværdien "url" i siden. Ikke noget mystik der, da siden kalder getFileContents() til at udføre denne "conditional include".
Avatar billede sostack Nybegynder
24. maj 2004 - 12:36 #11
Det er generelt / cross platform php

//sostack
Avatar billede monkeysee Nybegynder
24. maj 2004 - 13:29 #12
Sostack - jeg har nu installeret Apache2 m. PHP4, og selvom det ikke er en anbefalet kombination virker dit eksempel fint! Og jeg er sgu' imponeret over PHP's syntax - din kode fylder ikke ret meget, men selvfølgelig er jeg fyldt med sprgsm. som trænger sig på; specielt tænker jeg på at en del af mit eksempel handler om at finde matches på ".htm" extension, og så sortere dem efter hvornår de sidst er blevet ændret.Vil det være muligt med arrays i PHP, eller findes der andre/nemmere metoder til at sortere?

Sådan en funktion - hedder det i det hele taget funktioner i PHP? - kan i øvrigt også bruges til at vise hvornår der sidst er foretaget ændringer i mappen som helhed.
Avatar billede sostack Nybegynder
24. maj 2004 - 13:54 #13
Prøv med:
<?php
$diret = "."; //Den mappe du vil liste filerne fra, det eneste der skal rettes.
$handle = opendir($diret);
$counter = 0;
WHILE(false !==($file = readdir($handle)))
{
    if("." != $file && ".." != $file && (".htm" == substr($file, -4) || ".html" == substr($file, -5)))
    {
        $udskrives[$counter]["link"] = "<a href='$diret/$file'>";
        $fh = fopen($file, "r");
        $indhold = fread($fh, 256);
        $udskrives[$counter]["chg_time"] = filectime($file);
        $titel1 = explode("</title>", $indhold);
        $titel = explode("<title>", $titel1[0]);
        $udskrives[$counter]["link"] .= $titel[1] . "</a>";
        $counter++;
    }
}
arsort($udskrives);
reset($udskrives);
foreach($udskrives AS $key => $value)
{
    foreach($value AS $link => $time)
    {
        if("chg_time" == $link)
        {
            echo $link . "\t" . date("d-m-Y H:i:s", $time) . "<br />\n";
        } else {
            echo $link . "\t" . $time . "\n";
        }
    }
}
?>

//sostack
Avatar billede sostack Nybegynder
24. maj 2004 - 14:07 #14
Sådan:
<?php
$diret = "."; //Den mappe du vil liste filerne fra, det eneste der skal rettes.
$handle = opendir($diret);
WHILE(false !==($file = readdir($handle)))
{
    if("." != $file && ".." != $file && (".htm" == substr($file, -4) || ".html" == substr($file, -5)))
    {
        $counter = filemtime($file);
        $udskrives[$counter] = "<a href='$diret/$file'>";
        $fh = fopen($file, "r");
        $indhold = fread($fh, 256);
        $titel1 = explode("</title>", $indhold);
        $titel = explode("<title>", $titel1[0]);
        $udskrives[$counter] .= $titel[1] . "</a>";
        $counter++;
    }
}
krsort($udskrives);
reset($udskrives);
echo "<pre>";
foreach($udskrives AS $key => $value)
{
    echo $value . "\t" . date("d-m-Y H:i:s", $key) . "<br />\n";
}
echo "</pre>";
?>

Så sorterer den filerne, med de senest modificerede øverst.

//sostack
Avatar billede sukos Juniormester
24. maj 2004 - 14:22 #15
Der er nu ellers lidt "bøf" i dit script, sostack :O)

Hvis nu der er en masse javascript, før title?
Hvis nu <title> skrives <TITLE>?
Eller filer hedder .HTM og ikke .htm?

anyway, har osse prøvet lidt, men dog ikke med nogen former for sortering


<?php

$readdir = "/dir/"; // Dir som skal læses, med skråstreg først og sidst


function changed($var) {
return "Sidst ændret d. ". date("d-m-y H:i:s", filemtime($var));
}

function list_files($var) {
global $allfiles, $error_string;
$allfiles = array();
$error_string = "<br>\nFejl ved læsning af dir!<br>\nDet findes ikke";
$dir = $_SERVER["DOCUMENT_ROOT"] . $var; // Dir som skal læses igennem

if(is_dir($dir)) {
$string = "";
$types = array("htm", "html");

$path = opendir($dir);
while(false !==($file = readdir($path))) {

$ext = pathinfo($path . $file);

if(is_dir($path . $file) || !in_array(strtolower(@$ext["extension"]), $types)) {
continue;
}

$string .= "<br>\n<a href=\"". $_SERVER["PHP_SELF"] ."?file=".rawurlencode($file) ."\">". $file ."</a><br>\n";

$read = file_get_contents($file);
$s_pos = strpos(strtolower($read), "<title>");

    if(false === $s_pos) {
$string .= "Ingen titel";
    }else{
    $e_pos = strpos(strtolower($read), "</title>");
        if(false === $e_pos) {
$string .= "Ingen titel";
        }else{
$string .= substr($read, ($s_pos+7), ($e_pos-strlen($read)));
    }
}
$string .= "<br>\n". changed($file);

    }
closedir($path);
$allfiles[] = $string;

    }else{
$allfiles[] = $error_string;
  }

}

echo"<html><head><title>read html files</title></head>\n";
echo"<body>\n";
echo"<table><tr>\n";
echo"    <td valign=\"top\">Vælg en fil:";

list_files($readdir);

for($i = 0; $i < count($allfiles); $i++) {
echo $allfiles[$i];
}

echo"</td>\n";

if(isset($_GET["file"])) {
echo"    <td valign=\"top\">";
    if(file_exists($_SERVER["DOCUMENT_ROOT"] . $readdir . rawurldecode($_GET["file"]))) {
echo"<iframe width=\"800\" height=\"600\" scrolling=\"auto\" frameborder=\"0\" marginheight=\"10\" marginwidth=\"10\" src=\"". $readdir . rawurldecode($_GET["file"]) ."\"></iframe>";
    }else{
echo"<b>Forespurgte fil findes desværre ikke!</b>";
}
echo"</td>\n";
}

echo"</tr></table>\n";
echo"</body></html>";

?>
Avatar billede monkeysee Nybegynder
24. maj 2004 - 14:27 #16
Fedt, tak, point!!! Du har opnået gudestatus hos mig:-) Du kan i øvrigt se resultatet når Nørrebro festivalens hjemmeside (norrebro-festival.dk) går i luften i næste uge - forhåbentlig har jeg fået styr på the "missing pieces" til den tid.

Indtil da, ha' det rigtigt godt!

venlig hilsen,
nesby@irisworks.dk
Avatar billede sostack Nybegynder
24. maj 2004 - 14:29 #17
Hvis der kan være meget javascript først i filerne, kan man bare ændre $indhold = fread($fh, 256); til f.eks: $indhold = fread($fh, filesize($file)); så skal man skrive meget script-code ;-)

//sostack
Avatar billede monkeysee Nybegynder
24. maj 2004 - 14:31 #18
Og > sukos, vær ikke hård mod sostack, han kom hurtigt frem med et script som er en udemærket "primer" der fortæller en total PHP-newbie som mig hvordan det gøres. Det med at tjekke, og dobbelt-tjekke, er selvfølgelig detaljer som skal på plads, men som det (måske) fremgår at mit eget script er det en masse ekstra kode som faktisk fjerner fokus fra hvad der *egentlig* foregår.
Avatar billede monkeysee Nybegynder
24. maj 2004 - 14:33 #19
Og-og > sukos du har lige vist mig hvordan jeg pakker det hele ind i funktioner. Så du skal sgu' også have tak (sikken masse roser jeg deler ud i dag :-))
Avatar billede sukos Juniormester
24. maj 2004 - 14:36 #20
nej,nej, det var bestemt heller ikke for at være hård eller smartere! :O)
Og roser? jahhh, jow tak :O)
Avatar billede monkeysee Nybegynder
24. maj 2004 - 14:46 #21
Sukos > har lige prøvet dit script, det spiller bare!!
Avatar billede Ny bruger Nybegynder

Din løsning...

Tilladte BB-code-tags: [b]fed[/b] [i]kursiv[/i] [u]understreget[/u] Web- og emailadresser omdannes automatisk til links. Der sættes "nofollow" på alle links.

Loading billede Opret Preview
Kategori
Vi tilbyder markedets bedste kurser inden for webudvikling

Log ind eller opret profil

Hov!

For at kunne deltage på Computerworld Eksperten skal du være logget ind.

Det er heldigvis nemt at oprette en bruger: Det tager to minutter og du kan vælge at bruge enten e-mail, Facebook eller Google som login.

Du kan også logge ind via nedenstående tjenester