Jump to content

KevinM1

Moderators
  • Posts

    5,222
  • Joined

  • Last visited

  • Days Won

    26

Everything posted by KevinM1

  1. How did you come to that conclusion? Not to answer for ardyandkari, but I ran into that problem a couple years ago at my former place of employment. My boss (who knew nothing of teh intarweb other than games and porn) bought Windows hosting through GoDaddy because he thought he needed a Windows server for web pages to work on a Windows client machine. When I came in and was told to build our online store, I was shocked to learn that GoDaddy didn't have WAMP support. If you wanted PHP, you needed their Linux hosting. We put the store on Bluehost instead. I know that GoDaddy has since changed that, but in late 2006/early 2007 their Windows servers didn't have PHP installed.
  2. There are really two questions you have to ask: 1. Should all users be allowed to have those administration capabilities (which I put in bold) available to them from the outset? 2. Does it make sense to put functions that make sweeping system changes into the same class that previously allowed only individual changes? I can't think of a reason, other than wanting to save a few keystrokes, to shoehorn administration functions into a generic user class. This sort of thing is better left to an administration class of some sort that is responsible for largescale user manipulation.
  3. This. I hate having to go through several windows just to do some simple housekeeping. I prefer ICDsoft, Bluehost, and just about anyone else with a decent CP.
  4. Copycat. Since you're here (so-to-speak), I was wondering how you'd go about securing textareas while allowing users to post code. I look at a message board like this, which allows users to enter in both HTML and JavaScript (as well as just about everything else), and wonder how it's done without compromising security. Does htmlentities() offer protection? Or is it a combination of things?
  5. Eewww, putting JS somewhere other than the head is icky. ;-) If speed isn't a factor, why not wait for the DOM to load? <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd"> <html> <head> <title>Edit Sales People - OFFICE</title> <link rel="stylesheet" type="text/css" href="../include/style.css"> <script type="text/javascript"> window.onload = function() { document.getElementById("test").style.backgroundColor = "#FFFFCC"; } </script> </head> <body> <table> <tr> <td class="Light">Role</td> <td id="x">hello</td> </tr> </table> <div id="test">hellow</div> </body> </html>
  6. Private properties and methods should be used when you don't want the public to have direct access to them. It's easier to illustrate with properties, so here's an example: <?php class BadExample { public $password; public $SSN; } ?> In this example, someone's password and Social Security Number are public. This means two things: 1. All other code in the system can read this info directly: <?php $be = new BadExample(); $stolenPass = $be->password; $stolenSSN = $be->SSN; ?> 2. More common, and perhaps even more dangerous, all other code in the system can set this info directly: <?php $be = new BadExample(); $be->password = "It's peanut butter jelly time!"; $be->SSN = 007; ?> Our BadExample object is now more or less useless, as well as any other participant in the system that uses it. In well-designed systems, objects should vigarously protect their information, allowing the outside world to read/alter it only when necessary: <?php class GoodExample { private $password; private $SSN; public function getPass() { return $this->password; } public function setPass($pass) { $this->password = $pass; } public function getSSN() { return $this->SSN; } public function setSSN($newSSN) { $this->SSN = $newSSN; } } ?> Now, it doesn't look like much has been done. Afterall, the password and SSN can still be obtained and changed. The difference, though, is that direct access has been removed. This code forces the other system participants to go through an explicit process in order to do anything useful with its data. In other words, these methods (especially the set methods) can protect that data from tampering because they act as a secure gateway to that data: <?php class GoodExample { . . . public function setPass($pass) { if(!preg_match("/^[a-zA-Z0-9_]{16}$/", $pass)) { echo "Password must have letters, digits, or underscores and must be 16 characters long!"; } else { $this->password = $pass; } } ?> Private methods are a bit more rare, but the concept is the same. These methods tend to be utility functions that help with processing object data, but don't need to be available to the rest of the world. Protected properties and methods are simple as well. If you have data/methods that should be private, but want inheriting child classes to have them as well, make them protected in the parent class: <?php class GoodExample { protected $password; protected $SSN; public function getPass(){/* same code as above */} public function setPass($pass){/* same code as above */} public function getSSN(){/* same code as above */} public function setSSN($newSSN){/* same code as above */} } class GoodChild extends GoodExample{} $gc = new GoodChild(); $gc->setPass("1234567890123456"); $gc->setSSN("000-00-0000"); $pass = $gc->getPass(); $SSN = $gc->getSSN(); echo "Password: $pass -- SSN: $SSN"; ?> $password and $SSN are still private to the outside world, but the child class has access to them. Hope this helps!
  7. After doing some more research on this issue (mainly because I've never used sprintf() in my own code), I have a few more suggestions/comments: sprintf(), from everything I've read and heard, doesn't really do anything to protect one from SQL injection by itself. It does provide some typecasting, so if you have the following situation: <?php $input = "5 or not 0"; sprintf("INSERT INTO table (column1, column2) VALUES ($one, $two) WHERE something = %d", $input); ?> Only the integer 5 is substituted into the query string, as it expects an integer (%d), not a string. This doesn't provide any protection, though, if the query is indeed expecting a string at that location. The key lies in using mysql_real_escape_string() to escape potential metacharacters, and in using regex to ensure that the data coming in is valid.
  8. Hmm...I think that's a bit too general as you're specifically talking about someone inserting script tags (unless I'm missing the part you're referring to). Not all data validation requires the programmer to strip just script tags from the input. It's really more of an illustration of what damage a successful SQL injection can cause, which is good, IMO. In fact, if possible you should make that a section in and of itself -- common SQL attacks -- which describe common attacks launched from a compromised database. To get back to general data validation, you'd probably want to strip all tags from the input and perhaps even run the data through a profanity filter, especially if its a family friendly site. If you want to allow tags, you should definitely add a part to the tutorial illustrating how to do it safely. You should also check that inputed data is well-formed. People don't tend to have digits in their names (i.e. John Smith II is valid, John Smith 2 is not), phone numbers don't tend to have letters, etc.
  9. I assumed that you were talking about logins as that's what you call it in several places on the site. Login, to me, is not a generic term you can substitute for form input/data input. Login is a very specific instance of data input in which the user enters a username/e-mail address and password which gives them increased access to the site in question. This might be trivial to you, but since you're writing a tutorial, you should be certain that the language used is as precise as possible. Else, why use a term that isn't equivalent to that desired meaning (i.e. login != general data input). I, for one, would not allow the public to submit HTML or CSS unless I was running a message board like this. Then, yes (and obviously) I would modify my approach of scrubbing/validating user submitted data, although I would most likely still employ regex somewhere in the process. Yes, and that was somewhat intentional. Since I thought you were mainly refering to login info, I made my example deal with a username (hence the $name variable and form field). Obviously, most sites allow numbers for this, so a better regex would be: /^[a-zA-Z0-9_]+$/ To account for the underscore character as well. Here's another benefit to the regex method of form input validation: You not only ensure that the data is secure, you ensure that it's valid. Yes, sprintf() will remove the threat of SQL Injection, but merely using that does not ensure that the form input data submitted is useful in any way. Since you have to validate and secure the data anyway, why not do both at once? Honestly, I can't think of a reason not to go the regex route.
  10. Like always, it was a couple of syntax errors that screwed me up.
  11. I'm trying to create 'my own' (read: bits copied from a variety of sources) JavaScript library. I've decided to use a namespace methodology similar to that of the YUI library. Unfortunately, it looks like I have something weird going on with my naming. Everything will make more sense after I show the relevant pieces of code. My HTML is a simple form with one input used to test if the validation function I've incorporated is working. So, its code is: <html> <head> <title>JavaScript Library Test</title> <script type="text/javascript" src="js/MPlib.js"></script> <script type="text/javascript"> window.onload = function() { var inputForm = document.getElementById("inputForm"); inputForm.onsubmit = validate; function validate() { if(!MP.Form.Validate.validateEmail(this.elements["email"])) // <-- line giving me the error { alert("E-mail entry not valid!"); } } } </script> </head> <body> <form id="inputForm" name="form" action="#" method="POST"> E-mail: <input name="email" type="text" /> <input name="submit" type="submit" value="submit" /> </form> </body> </html> I get an error on the line I commented above. Specifically, the error occurs after I click submit. It is: This is odd, as MP is defined (although it, itself, is empty). Here's the relevant library code (apologies for the spacing...it looks like Notepad++'s tabs don't copy over): /** *This is my first attempt at building a JavaScript library. *While most of my code will use a pre-existing library (YUI, Scriptaculous, JQuery, Prototype, or Moo.fx), *I still have other helper functions I'd like to use. * *Date: May 12, 2008 */ /** *Global namespace */ var MP = {}; //----------------------------------------------------------------------------------------------- /** *Form namespace */ MP.Form = {}; //----------------------------------------------------------------------------------------------- /** *Form handling/validation namespace. */ MP.Form.Validate = { /** *Function to see if a required input has had information entered into it. * *@elem - element we're checking. *@getInputsByName - helper function. *@original - from John Resig's book Pro JavaScript Techniques */ checkRequired = function(elem) { if(elem.type == "checkbox" || elem.type == "radio") { return getInputsByName(elem.name).numChecked; } else { return elem.value.length > 0 && elem.value != defaultValue; } } //----------------------------------------------------------------------------------------------- /** *Helper function to find all input elements that have a specific name (good for those pesky checkboxes and radio buttons). * *@name - name of the elements we're looking for. *@original - from John Resig's book Pro JavaScript Techniques. */ getInputsByName = function(name) { //The array of input elements that will be matched. var results = []; //Counter to keep track of how many have been checked. results.numChecked = 0; //Find all input elements in the document. var inputs = document.getElementsByTagName("input"); for(var i = 0; i < inputs.length; i++) { //Find all inputs that have the name we're looking for. if(inputs[i].name == name) { //Add it to the array results.push(input[i]); //Remember how many of the fields have been checked, if any if(input[i].checked) { results.numChecked++; } } } return results; } //----------------------------------------------------------------------------------------------- /** *Function that validates an e-mail address. * *@elem - the element whose value we're checking. */ validateEmail = function(elem) { return elem.value == '' || /^[a-z0-9_+.-]+\@([a-z0-9-]+\.)+[a-z0-9]{2,4}$/i.test(elem.value); } //----------------------------------------------------------------------------------------------- /** *Function that validates an inputed URL. * *@elem - the element whose value we're checking. */ validateURL = function(elem) { return elem.value == '' || !elem.value = 'http://' || /^https?:\/\/([a-z0-9-]+\.)+[a-z0-9]{2,4}.*$/i.test(elem.value); } //----------------------------------------------------------------------------------------------- /** *Other validation functions to be added later. */ }; I fail to see how MP is not defined. Unfortunately the alert isn't firing at all, so I'm at a bit of a loss. Please help. EDIT: While I'm here, I have another issue. I have the following error in my library code: The code is: MP.DOM = { /** *Function to get/set element attributes. *It normalizes those tricky cases of 'for' = 'htmlFor' and 'class' = 'className'. * *@elem - element we're accessing *@name - name of the style *@value - value of what we're setting (if any) * *@original - From John Resig's book Pro JavaScript Techniques */ handleAttr = function(elem, name, value) // <-- error here { //Make sure a valid name was provided if(!name || name.constructor != String) { return ''; } //Figure out if the name was one of the weird naming cases name = {'for' : 'htmlFor', 'class' : 'className'}[name] || name; //If the user is setting a value, also if(typeof value != 'undefined') { elem[name] = value //If we can use setAttribute if(elem.setAttribute) { elem.setAttribute(name, value); } } //Return the value of the attribute return elem[name] || elem.getAttribute(name) || ''; } //----------------------------------------------------------------------------------------------- /** *Function to create a new DOM element. *It normalizes XHTML and HTML element creation. * *@elem - type of element we're creating *@original - from John Resig's book Pro JavaScript Techniques */ createElem = function(elem) { return document.createElementNS ? document.createElementNS('http://www.w3.org/1999/xhtml', elem) : document.createElement(elem); } }; Firefox's console tells me it's between the '=' and function(...). I can't figure out why it's choking on it, though.
  12. Ah, good point. It's just a habit I've gotten myself into.
  13. Wouldn't it be better to validate the incoming requests at the source instead of playing games with sprintf() and a custom function to strip JavaScript? I mean, neither would happen in the following case: <?php if(!preg_match("/^[A-Za-z ]+$/", $_POST['name'])){ //bad data } else{ $name = mysql_real_escape_string($_POST['name']); } ?> No numbers or special characters allowed in the example above. Only letters and spaces. This nullifies tags and the ' or 1=1-- business. I'm sure someone with more experience will chime in (and tell me I'm wrong ), but to me, it just makes more sense to scrub data at the source by using regex to allow only that which matches the pattern(s) past the gate. Then you can escape and insert it.
  14. AFAIK, so long as you link to your library code before linking to your specific client code, things should run fine. In other words: <script type="text/javascript" src="library.js"></script> <script type="text/javascript" src="specific-client-code.js"></script>
  15. Remember, <span> is an inline element. You might need to change it's display property to 'block' to give it a height property.
  16. I was talking about the C family. Is simula also part of the C family? nevermind i don't want to argue with you. or i think you misunderstood. Easy, killer.... You merely stated that 'c++ is the mother of oop,' which is false. Given that a newcomer was asking fundamental questions about programming languages, I felt it was appropriate to correct your erroneous statement. In other words, there's a fundamental difference between saying "C++ is the mother of OOP," which implies that C++ was the first programming language ever to support OOP, and "C++ was the first within the C family of languages to support OOP," which is correct, with the added bonus of being explicitly clear in its meaning. Not a huge issue, in the long run, but I figure it's best not to potentially confuse someone if it can be avoided.
  17. Actually, Simula was the 'mother' of OOP: http://en.wikipedia.org/wiki/Object_oriented Remember, though, that C# is not C++. There are important differences between the two. To the original poster, since you have some background with C++, I recommend the "Thinking in C++" books. They'll teach you the C++ Standard.
  18. Nice job, but a couple of things: First, and perhaps most important, the color scheme is pretty bad. An almost avocado green (on my monitor, anyway) with orange and white? It literally causes me to squint while looking at it. For your navigation links, I think it would make more sense for the arrows at the end to point >> instead of <<. Like others have said, putting a clock in a text box looks sloppy. Do you need it to actually display a working clock? Or would a simple timestamp (i.e. "April 29, 2008 -- 10:21 AM") in the upper corner suffice? I haven't gone through the actual markup, but you should always, at the very least, make the site look identical in both Internet Explorer and Firefox. Both display things differently. Still, don't be discouraged. You're off to a great start.
  19. Why use character codes when you can use regex? Comments are for the OP. function validateNumber(){ var num = document.getElementById('input').value; // <-- 'input' is a generic name...use the actual form input id var regex = /^[0-9]{3}$/; // <-- this says "3 characters that are in the class 0 thru 9" if(!num.match(regex)){ // <-- if the number DOES NOT match the pattern, give an error alert(num + " isn't a 3 digit number!"); return false; } else{ return true; } }
  20. Not sure you'd have an awful lot of luck charging people for things on a social networking site. i completely disagree with you! firstly: forget making billions, or even millions. it depends on the subject and whats its about: is it really giving something to someone? someone doesnt have to be anyone - just someone. hey presto: u have a little ecomerce venture. Um, no. Economics aren't that simple. You have to ask yourself two questions: Does OM2's social networking site offer anything unique that the competition hasn't capitalized on yet? Facebook and MySpace (to name two of the many out there) offer the following: music, videos, games, other addons/applications. Hell, I can learn Japanese through Facebook. What can you offer that they can't? Is whatever unique service/feature worth paying for? Will it be worth paying for after the competition copies it, or makes an even better version? I'm not trying to be the turd in the punchbowl, but if you're serious about making money with this project, you've got to ask yourself the hard questions. People aren't going to fork over their (or their parent's) hard-earned money just because you're (assumingly) a nice person.
  21. Are both machines viewing the page with the same kind of browser?
  22. I'm familiar with the basics of JavaScript, but would like to learn more about its more advanced features. Specifically, doing things with custom objects, dealing with closures, the whole 'loss of scope' thing I've heard about, that sort of thing. I want to get real comfortable with JavaScript before trying my hand at AJAX. I'm the kind of guy who learns best with an actual book in my hands, so are there any decent, up-to-date resources (read: books) that someone could recommend? And no, w3schools doesn't qualify. Thanks!
  23. You need to reverse that, so: $controller = FrontController::getInstance(); //you need an instance before you can play with it $controller->setPageDir(PAGE_DIR); //note how it's not a static function $controller->dispatch(false); With your setup, I think the easiest thing to do is simply ensure that whenever you set the $pageDir variable in one object, you do the same for the other. That option leaves something to be desired if you really want to have that info available across the board. You could always refactor and create another class that holds/sets configuration data like this so your FrontController and View classes can retrieve it from there. These objects are typically refered to as registry objects. You register application info with them and any other class that needs that info can retrieve it. I have some sample code you can look at if you're interested. With ActionController, View, and $pageDir, it's a simple matter of declaring it as a protected static variable inside ActionController. I think I messed up previously and had it private, but it really should be protected. Like I said before, you're not instantiating an ActionController because it's abstract. But, since it's the base/parent class, you should be putting whatever functionality you want all its child classes to have within it. So, anything that's not specific to View should be put in ActionController. Just a note about the singleton(s). Remember to assign getInstance() to a variable like I showed above. This gets your hands on the object itself. Then you can play with it. Or, if you don't want direct access to it, and just want it to run, you can do something like (my test front controller): <?php class MP_controller_Controller{ private function __construct(){} //private constructor because it shouldn't be instantiated directly static function run(){ $instance = new MP_controller_Controller(); //$instance IS NOT a property because we don't need the client code to have direct access. We just want it to run once per request. The constructor works because we're calling it from WITHIN the object itself. It's not private to itself. $instance->init(); $instance->handleRequest(); $instance->display(); } private function init(){} //nothing to initialize yet, but there for the future private function handleRequest(){ $request = new MP_controller_Request(); //either $_POST or $_GET...the rest is separate OOP stuff $commandFactory = new MP_command_CommandFactory(); $command = $commandFactory->getCommand($request); $command->execute($request); } private function display(){ //display username if they logged in $sessReg = MP_base_SessionRegistry::getInstance(); //another singleton, this is a registry that deals with session info if(!$sessReg->isEmpty()){ $user = $sessReg->getUser(); if($user){ echo "Welcome back, {$user->getName()}<br /><br />\n\n"; } } } } ?> <?php /* client code */ MP_controller_Controller::run(); ?>
  24. For the page directory, why not try: <?php abstract class ActionController{ private static $instance; private static $pageDir = 'something'; //default value private function __construct(){} public static function getInstance(){ if(!self::$instance){ self::$instance = new self(); } return self::$instance; } public function setDir($pageDir){ self::$pageDir = $pageDir; } public function getDir(){ return self::$pageDir; } . . . } class View extends ActionController{} $view = View::getInstance(); $view->setDir('/home/views/'); echo "{$view->getDir()}"; ?> As far as getting $pageDir from ActionController to View goes, remember that ActionController is abstract. You're not going to be instantiating it, unless you decide to not make it abstract. That said, I put the mechanisms for handling it in the base ActionController class because that's the most logical place to put it. Unless the View class requires a different implementation than its parent -- in which case there's little use in making it extend ActionController -- there's no need to put it there. In any event, ideally, the page directory will either be hardwired into your script, which is why I assigned it a default (albeit non-legit) path within the class itself, or it will be obtained from another source, such as an external configuration file, which is why I added the setDir() method. Something to keep in mind: singletons are essentially global variables. So, you need to be sure that for important things, like the value of the directory that holds your views, you're not overwriting/changing that value in other areas. You may want to add a static flag to the class which is triggered when setDir() is called, so the directory can only be set once.
  25. You should post your code directly rather than links. PHP doesn't show up when trying to view source code from a site.
×
×
  • Create New...

Important Information

We have placed cookies on your device to help make this website better. You can adjust your cookie settings, otherwise we'll assume you're okay to continue.