Een paar maanden geleden heb je geleerd hoe je een in-place bewerkingssysteem kon creëren. Vandaag zullen we een stap verder gaan met het maken van een eenvoudige backend, waardoor onze website dat ook kan doen onthouden de wijzigingen die we hebben doorgevoerd.
Met alle drukte rondom Web 2.0 is gebruiksgemak nu veel belangrijker dan ooit. Sommige gebruikers kunnen hun content bewerken zonder naar een andere pagina te hoeven gaan. Veel grote namen gebruiken dit patroon al met groot succes. Als je Flickr hebt gebruikt, heb je dit waarschijnlijk in actie gezien.
Vandaag gaan we de eerdere versie verbeteren: sommige bugs verwijderen, enkele functies toevoegen en, nog belangrijker, alle gegevens opslaan in een echte database voor retentie. Geïnteresseerd? Laten we meteen beginnen!
Ten eerste hebben we een database nodig om de informatie op te halen en vervolgens, indien nodig, de gegevens bij te werken. Laten we voor deze oefening een tabel met willekeurige gegevens instellen.
Ik had al een database met de naam inplace met een tabel genaamd gegevens op mijn ontwikkelserver. Voor ons gebruik zullen we een andere tabel toevoegen.
Ik gebruik meestal phpMyAdmin voor het uitvoeren van mijn SQL-query's. Klik op het tabblad SQL en plak in de volgende query:
CREËER TAFEL ALS NIET BESTAAT 'inplace' ('field' varchar (120) NOT NULL, 'value' text NOT NULL, PRIMARY KEY ('field')) ENGINE = MyISAM; INSERT INTO 'inplace' ('veld', 'waarde') VALUES ('naam', 'ben Siddharth'), ('passie', 'hou van werken met het web'), ('beroep', 'ben een freelancer' ), ('werk', 'schrijf voor Net Tuts'), ('url', 'is te vinden op www.ssiddharth.com'), ('punch', 'laat je nooit in de steek of geeft je op :) '), (' ontwerp ',' Haal ontwerpgoedkeuring van Yusuf '), (' factuur ',' Stuur een factuur naar Drew '), (' onderzoek ',' Start onderzoek naar Pallav \ 's project'), (' bespreek ',' Spreek met Harnish over nieuwe ideeën '), (' debug ',' Controleer Aditya \ 's site voor het renderen van bugs'), ('meet', 'Ontmoet met Clintson om nieuw project te bespreken');
Als alles goed is verlopen, zou u het volgende scherm moeten zien:
Een kijkje op de tafel:
Omdat ik expliciet de eenvoud van de demo wilde behouden en alleen de mensen aan de achterkant wilde toevoegen, heb ik de structuur van de tabel heel eenvoudig gehouden. Voel je vrij om het aan te passen en uit te breiden in je projecten.
Nu de voorbeeldtabel is gemaakt en vooraf is gevuld met een aantal testgegevens, kunnen we doorgaan naar de daadwerkelijke back-end.
Omdat we vaak toegang zullen hebben tot de database om gegevens te lezen of om de gegevens die het bevat bij te werken, is het verstandig om een configuratiebestand te maken met de relevante gegevens. Maak een bestand met de naam db.php en plak het volgende erin.
Niets bijzonders hier. We definiëren alle relevante details, maken verbinding met de host met behulp van de gegeven gebruikersnaam / wachtwoord-combinatie en selecteren vervolgens de relevante database voor manipulatie onderweg.
De redacteur zorgt voor het lezen van de database en het uitvoeren van de gegevens in een specifiek formaat, zodat het voor ons gemakkelijk is om relevante gegevens terug naar de server te sturen met vermelding van welk record moet worden bijgewerkt. We zullen er in een oogwenk meer over praten.
De code verandert niet significant van de statische HTML-code van de eerdere versie. We moeten de gegevens echter dynamisch maken. Dus in de originele HTML-code, dit:
is vervangen door:
'$ Row [ 'value'].''; ?>
'$ Row [ 'value'].''; ?>
Omdat de tabel klein is, selecteren we gewoon alles uit de tabel, maar vragen we om alleen de eerste 6 elementen te retourneren. Vervolgens herhaal ik het en voer ik het uit li elementen. Let vooral op het feit dat elk li elementen krijgt zijn ID kaart attribuut ingesteld op de naam van het veld waarvan het de waarde krijgt. Dit wordt later gebruikt in de gegevens die naar de server worden teruggestuurd om aan te geven welk record moet worden bijgewerkt.
Ik ben me ervan bewust dat het blootstellen van de naam van het veld op deze manier een beveiligingsrisico kan vormen, maar in een goed beveiligde omgeving denk ik niet dat dit tot problemen zal leiden. Anders zou je hier gewoon aliassen kunnen gebruiken en een reverse lookup doen aan de serverkant. Laat je creatieve sappen daar stromen. Voor een zeer ongecompliceerde demo leek het nogal overdreven.
Vergeet ook niet het db.php bestand dat we eerder hebben gemaakt naar de editor. Deze regel zorgt ervoor.
Vergeet na het maken van de bewerkingen het bestand niet op te slaan met een .php uitbreiding.
De handler is waar de pagina de details naartoe zet. Dit zorgt ervoor dat wordt gecontroleerd of gegevens daadwerkelijk naar de pagina zijn verzonden en zuivert dan de verzonden gegevens en werkt vervolgens de relevante waarden bij.
Maak een bestand met de naam handler.php en plak in het volgende:
Een vrij eenvoudige zaak. Laat me elke stap in detail uitleggen.
Omdat we de database moeten manipuleren, nemen we eerst de db.php bestand dat we eerder hebben gemaakt.
Vervolgens controleren we of beide vereiste variabelen, veld-- waarde die ons vertelt welk veld moet worden bijgewerkt en waarde - de waarde die moet worden bijgewerkt, worden als POST-variabelen naar de handler verzonden. Als dat zo is, kunnen we doorgaan met het daadwerkelijke werk. Zo niet, dan gebeurt er niets.
Zodra we hebben geverifieerd dat de variabelen zijn verzonden, kunnen we doorgaan met het opschonen van de gegevens voor invoeging in de database. Om het zo eenvoudig mogelijk te houden, gebruiken we de mysql_real_escape_string functie om onze gegevens te zuiveren. Deze functie ontsnapt aan de speciale tekens die aanwezig zijn in de doorgegeven tekenreeks. Als het wordt doorgegeven in niet-gereinigd, is onze code onderhevig aan SQL-injectieaanvallen.
Nu we hebben gecontroleerd of de gegevens veilig zijn, kunnen we het relevante record bijwerken. Ik ga ervan uit dat dit deel geen uitleg behoeft, omdat het een heel eenvoudige SQL is. In termen van de leek, in de inplace tafel, veranderen veld bijbehorende waarde voor waarde.
Als alles volgens plan verloopt, retourneert u een waarde van 1 die door ons script worden vastgelegd om de uitkomst van de transactie te bepalen, zodat deze overeenkomstig kan doorgaan. Ik zal later meer uitleggen. Houd er alstublieft rekening mee dat ik in dit geval alleen maar rapporteer of de poging is gelukt of mislukt. In uw project wilt u mogelijk veel gedetailleerdere info retourneren voor het geval er een fout optreedt. U bent niet beperkt tot mijn uiterst eenvoudige implementatie.
Nu de back-end is geconstrueerd, is het tijd om het voorste deel van het project te bewerken om het met de server te laten communiceren. We zullen ook kijken naar de implementatie van een nieuwe functie langs de weg.
Een van de klachten van de oude versie was datacorruptie wanneer bepaalde acties in een specifieke volgorde werden uitgevoerd. Dit kwam door mijn extreme behoefte aan eenvoud en beknoptheid die me uiteindelijk leidde tot het negeren van dat specifieke scenario. Niettemin zullen we dat vandaag corrigeren.
Ik ga ervan uit dat je de oude JavaScript-code in de buurt hebt om te vergelijken en te bewerken.
In de eerste versie werden globale variabelen gebruikt om de oorspronkelijke gegevens te bewaren die in bepaalde gevallen tot onverwachte resultaten hebben geleid. We zullen dit eerst corrigeren.
De gemakkelijkste manier om dit te corrigeren is om gewoon een verborgen invoer naast de originele invoer toe te voegen en deze als een buffer te gebruiken. Omdat het on-the-fly wordt gemaakt en vernietigd en specifiek is voor dat element alleen, kunnen we zo veel mogelijk elementen zo veel mogelijk tijd zonder hikken bewerken / opslaan / verwijderen..
De oude replaceHTML functie wordt bijgewerkt naar:
function replaceHTML () var buffer = $ (this) .html () .replace (/ "/ g," ""); $ (this) .addClass ("noPad") .html ("") .html ("Wijzigingen opslaan Wijzigingen verwijderen ") .unbind ('dblclick', replaceHTML);
Geen grote bewerking hier. Eerst maken we een interne variabele genaamd buffer om de oorspronkelijke waarde te behouden. Vervolgens zuiveren we de HTML-inhoud van het bovenliggende element en injecteren we die van onszelf. Naast het oorspronkelijke fragment voegen we een verborgen tekstvak toe waarin de oorspronkelijke waarde behouden blijft. Hier is niets anders veranderd.
De eerdere iteratie bond vergelijkbare maar afzonderlijke functies voor elk van de functionele koppelingen. We zullen ze hier verenigen.
function handler () var selector; if ($ (this) .hasClass ("btnSave")) selector = "editBox" else selector = "buffer" $ (this) .parent () .html ($ (this) .siblings ("form") ) .kinderen ("." + selector) .val ()) .removeClass ("noPad editHover"). bind ("dblclick", replaceHTML); return false;
In plaats van het gebruik van anonieme functies zoals de vorige keer, gaan we een normale functie gebruiken. We gaan alleen kleine delen van de functie bewerken om zowel aanvragen voor opslaan als verwijderen af te handelen.
We declareren eerst een variabele met de naam keuzeschakelaar die de selector vasthoudt om te gebruiken tijdens het updaten van de li elementen. editbox is de klasse toegewezen aan het zichtbare tekstvak en buffer is de klasse die is toegewezen aan het verborgen tekstvak waarin de oorspronkelijke waarde is opgeslagen.
Omdat we de gebeurtenishandlers verenigen, moeten we controleren op welke link is geklikt. We zien eerst of de aangeklikte link een klasse heeft btnSave. Als dat zo is, wil de gebruiker de bewerkingen opslaan en daarom wijzen we de waarde toe van editbox naar de keuzeschakelaar variabel. Als niet, buffer is toegewezen.
De rest van de handler blijft hetzelfde als de oude versie, behalve dat de selector dynamisch wordt geïnjecteerd op basis van de actie in plaats van dat deze hard in de functie wordt gecodeerd. Als je hier verdwaald lijkt, kijk dan naar het eerste deel van de serie om te begrijpen wat het laatste blok doet. In wezen injecteren we de waarde van het geselecteerde tekstvak in het bovenliggende element li element en koppel de oorspronkelijke gebeurtenishandler opnieuw.
Vergeet niet om de gebeurtenishandlers voor elke link bij te werken. De volgende voering zorgt voor dat:
$ (".btnSave, .btnDiscard"). live ("klik", handler);
Als je je afvraagt waarom ik de leven functie hier, verwijs naar het eerdere artikel.
Met alle bugs platgedrukt en de code in het algemeen wat aangescherpt, kunnen we beginnen met het implementeren van de feitelijke functionaliteit.
Voordat we de gegevens naar de server kunnen verzenden, moeten we een manier vinden om relevante gegevens terug naar de server te sturen. In dit geval hebben we 2 details nodig om een succesvolle bewerking te maken.
Het eerste deel is tamelijk eenvoudig omdat we een echt tekstvak hebben met de waarden die naar de server moeten worden verzonden. Het tweede deel heeft een beetje werk nodig.
Denk er tijdens het maken van de editor aan dat we de primaire ID van de tabel hebben gebruikt als ID kaart attributen aan elk li element? We gaan hier gebruik van maken. We zullen gewoon een ander verborgen tekstvak maken dat de waarde zal bevatten die dan weer naar de server kan worden teruggestuurd.
function replaceHTML () var buffer = $ (this) .html () .replace (/ "/ g," ""); $ (this) .addClass ("noPad") .html ("") .html ("Wijzigingen opslaan Wijzigingen verwijderen ") .unbind ('dblclick', replaceHTML);
De replaceHTML functie moet worden bijgewerkt zoals zo. Het enige verschil is de toevoeging van verborgen tekstvak met de naam veld-. We gebruiken jQuery's attr functie om toegang te krijgen tot de li element ID-kenmerk en gebruik het als de waarde van het tekstvak.
Op naar de AJAX-implementatie dan. We gaan de standaard van jQuery gebruiken Ajax functie hier.
function handler () // Previous code if ($ (this) .hasClass ("btnSave")) var selector = "editBox"; var str = $ (this) .siblings ("form"). serialize (); $ .ajax (type: "POST", async: false, timeout: 100, url: "handler.php", data: str, success: function (msg) code = msg;,); if (code == 1) alert ("Succes"); else alert ("Failure"); // Rest van de code
Aangezien we de gegevens alleen naar de server hoeven te verzenden wanneer de gebruiker op de relevante link heeft geklikt, kapselen we alle code in de als blok dat we eerder hebben gemaakt om te controleren op welke koppeling is geklikt.
Ik maak gebruik van de Ajax functie omdat ik vind dat het de meest robuuste is. Ten eerste, serialiseer ik de gegevens die het bovenliggende formulier bevat, zodat het kan worden gepost naar de server. Vervolgens bel ik de Ajax functie instellen van alle relevante details zoals nodig, inclusief het type verzoek dat moet worden gedaan - POST en de URL waarnaar moet worden gepost. We specificeren ook dat de gegevens die we eerder hebben geserialiseerd naar de server moeten worden verzonden.
Meestal zou je de ingebouwde gebruiken succes en fout callbacks om verdere wijzigingen aan te brengen, maar ik heb ervoor gekozen om dit hier niet te doen. In plaats daarvan neem ik alleen de tekst op die door de server is teruggestuurd. Als er 1 wordt geretourneerd, een waarde die we hebben geconfigureerd om onze handler terug te sturen als alles correct is gebeurd, waarschuwen we de gebruiker om hem dit te laten weten.
Waarschuwingen zijn een vrij eenvoudige manier om de gebruiker bij te werken met de status van de actie. Met dat in gedachten zullen we het waarschuwingssysteem schrappen en in plaats daarvan een eenvoudige statusbalk aan de onderkant implementeren die deze veranderingen weerspiegelt.
We hebben hier niets speciaals nodig. We hebben alleen een simpele nodig div element dat we kunnen manipuleren. We zullen dat rechtstreeks in de editor moeten toevoegen.
Noteer van de ID kaart attribuut. We zullen het later gebruiken.
In het belang van hergebruik van code, zullen we een helperfunctie maken die de statusbalk indien nodig bijwerkt.
functie UI (status) var status = ; status.Ready = "Gereed"; status.Post = "Uw gegevens opslaan. Een ogenblik geduld ..."; status.Success = "Succes! Uw bewerkingen zijn opgeslagen."; status.Failure = "Pogingen om gegevens op te slaan zijn mislukt. Probeer het opnieuw."; var background = ; background.Ready = "# E8F3FF"; background.Post = "# FAD054"; background.Success = "# B6FF6C"; background.Failure = "# FF5353"; $ ("# status"). animeren (opaciteit: 0, 200, functie () $ ("# status"). html (status [staat]). css (achtergrond: achtergrond [staat]). animeren (opacity: 1, 200));
De functie die we hebben genoemd, UI, neemt de status van de statusbalk als parameter. Binnen de functie creëren we twee objecten: staat houdt de relevante tekst en achtergrond bevat de achtergrondkleuren van de statusbalk.
We kunnen de tekst en de achtergrondkleur van de statusbalk net bijwerken, maar hier bij Net Tuts zijn we er niet zo uit. :)
We gaan gebruik maken van jQuery's bezielen functie om op een elegante manier de statusbalk te animeren. Ten eerste animeren we de dekking op nul. Vervolgens werken we de tekst- en achtergrondkleur bij en animeren deze vervolgens weer volledig zichtbaar.
Let vooral op het feit dat de logica die wordt gebruikt om de waarden bij te werken, is ingesloten in een anonieme functie en wordt doorgegeven als het terugbellen naar de oorspronkelijke animatie. Op deze manier zal de balk animeren tot nuldekking en vervolgens wordt alles bijgewerkt. Als de animaties worden geketend, worden de tekst- en achtergrondkleuren bijgewerkt net nadat de initiële animatie start, wat leidt tot een zeer schokkend effect.
Toevoegen aan de gebruikersinterface en het bijwerken van de statusbalk is nu een fluitje van een cent. In plaats van de eerder gebruikte waarschuwingen, moeten we de UI functie.
Het eerdere blok dat de ajax-oproep opvolgt, kan nu worden vervangen door:
if (code == 1) UI ("Succes"); else UI ("Failure");
Vergeet ook niet om toe te voegen UI ( "Ready"); wanneer de pagina wordt geladen, weet de gebruiker dat het systeem klaar is voor manipulatie en UI ( "Post"); wanneer de gegevens op de server worden gepost.
Wanneer u uw eigen staten aan de taakbalk toevoegt, let er dan op dat de tekenreeks die we als parameter naar de functie verzenden, rechtstreeks naar de eigenschap van het object is.
Het laatste waar we naar moeten kijken, is dat als de poging om de gegevens op te slaan mislukt, de bijgewerkte tekst nog steeds bewaard blijft. Dit lijkt nogal contra intuïtief. Als de poging om de gegevens op te slaan mislukt, moeten we ervoor zorgen dat de oorspronkelijke tekst wordt teruggeplaatst, zodat de gebruiker weet dat de gegevens niet zijn opgeslagen.
Om dit te corrigeren, moeten we het wijzigen keuzeschakelaar variabele in het geval dat we een fout tegenkomen.
if (code == 1) UI ("Succes"); selector = "editBox"; else UI ("Failure"); selector = "buffer";
Als de waarde met succes is bewerkt, veranderen we de waarde van de relevante variabele in editbox. Maar als de poging is mislukt, moeten we de nieuwe waarde vervangen door de oude waarde. Dus we wijzen het toe buffer naar de variabele, zodat de waarde terugkeert naar de oorspronkelijke waarde.
En daar heb je het. Hoe u een gebruiksvriendelijke functionaliteit aan uw projecten kunt toevoegen. Hopelijk heb je deze tutorial interessant gevonden en dit was nuttig voor jou. Voel je vrij om deze code elders in je projecten en hier te gebruiken als je in de problemen raakt.
Houd er rekening mee dat dit systeem is ontworpen met de primaire bedoeling om de hieraan verbonden technieken te leren, niet als een productiesysteem dat is ontworpen om in bestaande systemen te integreren. Dit is meer een fundament waarop ik mensen aanmoedig om op te bouwen en te verbeteren.
Vragen? Leuke dingen om te zeggen? Kritiek? Klik op het gedeelte Opmerkingen en laat een opmerking achter. Happy codering!
Wist je dat je tot $ 600 kunt verdienen voor het schrijven van een PLUS tutorial en / of screencast voor ons?? We zijn op zoek naar diepgaande en goed geschreven tutorials over HTML, CSS, PHP en JavaScript. Als je van het vermogen bent, neem dan contact op met Jeffrey via [email protected].
Houd er rekening mee dat de daadwerkelijke compensatie afhankelijk is van de kwaliteit van de laatste zelfstudie en screencast.