Jump to content

mac_gyver

Staff Alumni
  • Posts

    5,532
  • Joined

  • Days Won

    189

Everything posted by mac_gyver

  1. as far as a user that already has a profile landing on this page, the same code can be used to edit an existing profile, by retrieving the existing data (see the get method/display code @line 57 in the following.) example code that addresses or shows how it would look for the item#1 list - <?php session_start(); // access security - must be logged in to access this page if(!isset($_SESSION['user_id'])){ // either redirect to somewhere else or output a message header('location:your_login_page_for_example'); exit; // prevent the rest of the code from running } $addProfileForm = htmlentities($_SERVER['PHP_SELF']); // form action try{ // start of database dependent code require('Connections/database.php'); // assuming that both the get method/display code (form) and form processing need a database connection // post method form processing if ($_SERVER['REQUEST_METHOD'] == 'POST') { $errors = array(); // array to hold errors $data = array_map('trim',$_POST); // copy and trim all post data (if the form has any arrays, you need to use a function like array_walk_recursive() instead of array_map()) // if you have multiple-forms, you would conditionally run the correct section of form processing code by testing for a form field or a field value that uniquely identifies which form was submitted // addprofileform form processing code - //check if there is an existing record in DB $query = "SELECT COUNT(*) FROM userProfile WHERE user_id = {$_SESSION['user_id']}"; $stmt = $database->query($query); $number_of_rows = $stmt->fetchColumn(); if ($number_of_rows > 0) { $errors[] = "There is an existing record. You cannot insert another profile! Either update the old one, or delete to insert again."; } if(empty($errors)){ // if no errors at this point, continue with validation // all your form field validation code would go here, using elements in the $data array (a trimmed copy of the $_POST data) } // done with validation, if no errors, use the data - if(empty($errors)){ // your code to insert the data and move the uploaded file would go here... } // if no errors at this point, redirect to the exact same url of this page to prevent the browser from resubmitting the data by causing a get request for the page if(empty($errors)){ $host = $_SERVER['HTTP_HOST']; $uri = $_SERVER['REQUEST_URI']; header("Location: http://$host$uri"); exit; } // if there were errors in any of the above form processing code, continue on this page, displaying any errors, redisplay form, (re)populate the form fields with data... } // end of post method form processing // get method/display code (if any) - get/produce data that's needed to display the page // to edit existing data, if the $data array is empty at this point, retrieve any existing data from the database table } catch(PDOException $e){ // end of database dependent code, handle any errors $status = empty($query) ? 'Connection failed':" Query failed: $query"; // application message trigger_error("$status, Error: {$e->getMessage()}, File: {$e->getFile()}, Line: {$e->getLine()}"); // user message $errors[] = 'Sorry, this page is not working at this time.'; } // done with the database, destroy any pdostatment resource and close connection $stmt = null; $database = null; // the html document that uses any data from the above code starts here - ?>i'll get back to you on any questions you posted in your reply above, that don't seem to be addressed by this example code.
  2. there are two main problems with the php code - 1) it has logic problems and code that isn't using the correct variables/values/database fields. 2) it is repetitive, resulting in a wall of code that makes it hard to even understand what the code is actually doing. your code tells us a story, the story of what you are trying to accomplish. if we cannot deduce from reading your code what it is actually doing, we cannot help with it. for item #1 - 1) the form processing code requires that the current visitor be logged in. therefore, the php code should not do anything unless there is a logged in visitor. the form page also requires that the current visitor be logged in and should not display the form unless there is a logged in visitor. 2) the php code that you posted is there to process the form submission. therefore, it should be inside of a conditional statement testing if the form was submitted. the code to test if a record already exists should be inside of the form processing conditional statement. 3) the userProfile table should use the user_id, not the username to associate the data in it with the user. this will simplify the SELECT query. then, just use $_SESSION['user_id'] to find if there is already a row in the userProfile table. 4) the SELECT query does not contain any bound input parameter, so, there no point in using a prepared query. 5) since there's no :id placeholder in the SELECT query, either the bindvalue() or the execute() statement are throwing errors for the current code. have you set the PDO error handling to use exceptions? you would be getting an uncaught exception to alert you to problems with the database statements (and you can then add try/catch logic in your code to handle database errors all in one place.) using exceptions will mean that you don't need to have conditional logic around every database statement (btw - the one place you are testing if a database statement failed, the first prepare(), the error message indicates that the there was an error executing the query. the prepare() statement doesn't execute the query, only prepares it.) 6) you are setting the $username variable to a 1. even if your SELECT query was using a bound input parameter/value correctly, it is an id and the variable you are using should be named to match what is being used and the value should come from the correct place, $_SESSION['user_id'], not a fixed value in your code. 7) your insert query for the userProfile table, doesn't contain a username field, so either your SELECT query is wrong or your INSERT query is wrong. the UPDATE query for the picName is also trying to use WHERE id = $_SESSION['user_id']. the id won't be the user's id. the id will actually be the $newID value. $statement->fetchColumn() fetches the first column from the SELECT query. however, your query is not selecting a value that indicates how many rows the query matched, so the logic using the fetchColumn() value doesn't mean anything. for this to work, you would need to SELECT COUNT(*) in the query. this is one of the reasons why your code is ignoring the select query. you are also testing if the value is > 1. the test should be if it is > 0 to find if there already a row in the database table. 9) you should trim() all the form data at once, so that you don't have to keep repeating statements in the code using the values. 10) you shouldn't exit; after any of the errors have been detected. you want the code to finish so that it can display the error messages. 11) $errors[] = ("some message!"); the () are not needed and in fact cause php to do extra work (evaluating an expression) and add clutter to the code. 12) you have some statements starting at line 610 that don't have a query they belong with. why are those lines in your code? 13) for the header() statements on lines 625 and 627, there is no $returnURL variable in the code, so there's no place for those redirects to go to and if you were redirecting to somewhere, how would you be able to print the errors that in the $errors array? 14) i didn't specifically look for any problems in the all the radio button code. see the next item - for item #2 (while this sounds like advanced programming, after you do it once, you can reuse it and it will simplify all the form/form-processing code that you write) - when you have code (including html for form fields) that gets repeated over and over, where the only thing that changes are the values that get operated on, you need to use a different programming technique. instead of writing out all the possible lines of code yourself, you need to let php dynamically process data or dynamically produce html content. when you have a form and form processing code, you can create an array that defines everything about the form fields and the validation you want for each field. then, to produce the form or validate the form data, you just loop over the array that defines everything to tell just one instance of the code what to do. some of the things you need to define in the array to produce the form are - 1) field type - text, radio, ... 2) field name (using the field name, which must be unique anyway, as the array index/key is helpful) 3) a display legend in the case of checkbox/radio buttons, you can use an array within the array to define the information for each set of checkbox/radio buttons. some of the things you need to define in the array to process the form data are validation rules, such as required - i.e. not empty, format functions/parameters - i.e. the filter_var() function, with the FILTER_VALIDATE_EMAIL parameter for the email field or the strlen function and a minimum/maximum value for fields that must meet a certain length, and error message text for each validation rule.
  3. and as someone already mentioned, your code isn't using, nor does it need, the $variable = $row[index_name]; ...assignment statements. the time you spent putting those in, and now in changing them, isn't accomplishing anything, because your code isn't using those assigned variables and the only way you wouldn't know this is if you aren't looking at what you are doing. at this point, i don't think you are even looking at your code, just throwing random things against the wall to see if any of it sticks, and then dumping it on help forum(s) to get someone to put the code together the correct way for you. that's not you doing or learning programming. that's randomly trying things and almost never results in code that works.
  4. if your bom/cart is memory/session based, to display it with pricing, you would extract all the productId's (since these are array keys now, you can use array_keys() to do this all at once.) you would then implode the array of productId's to make a comma separated list that will get used in ONE database query, using an IN(...) term in the WHERE clause, to retrieve all the prices for those productId's, and store the result in an array, using the productId as the array key. as you loop over the contents of the bom/cart to display it, you would use the productId to get the price from the array you just made from the single query. if your bom/cart is database table based, you would just join the bom/cart with the pricing table, then just retrieve and display the results.
  5. if you mean the three dates near the end of your form, that you are using the same variable to populate, because there's only one date field being selected in your query? i would say the problem is because you are not selecting three different dates in your query.
  6. your form code is not using the variables that you assigned values to in the loop. in fact, why are you looping to retrieve one row. if you eliminate the loop, just fetch the row from the database, and forget about all the assignment statements, your code will work, because the form code is using the $row[...] variables that the fetch statement would populate. if you are not getting any php errors, i seem to recall that php changed at some point so that accessing an associative array index on a null/false value doesn't throw undefined index error messages.
  7. i was going with - ... BETWEEN startdate AND IFNULL(enddate,'9999-12-31')
  8. didn't see this thread before. the 'correct' way of doing this is to store the pricing information in a table using the productId, the start date (or datetime) and the end (or a NULL) date (or datetime.) each time the price changes for an item, you would set the end date (or datetime) for the previous price and insert a new row with the start date (or datetime) and the new price. any query to calculate the price would use the date (or datetime) of the quote to match the correct pricing information. any chance that your thread about the switch/case statement taking a long time is doing a ton of database queries (in a loop) that could account for the bad performance?
  9. is this shared web hosting, where there are a number of accounts running on the same server and you are using the default/shared location for your session data files?
  10. the code you posted above is only calling other code that's actually doing the work. without the relevant code, we cannot possibly tell you anything about why it isn't working or even what to look at next to find out more about what's going on.
  11. about the only way you would get that error is if you hadn't saved the contents of the pet.php file at the time you ran the pettest.php code, i.e. pet.php exists, but it is empty.
  12. ^^^ you are probably fetching one row before the start of your loop or you sql query is wrong. ^^^ the code you showed us is fetching the database rows into $e, not $d. $d must be some other variable from before the start of this code. if you are running the query/code you posted in this thread inside of a loop, you shouldn't. you should form and run ONE JOINed query that gets all the related data at one time.
  13. i would say yes. i have done a lot of BOMs/estimating for industrial controls, at the $1.5M level for entire plants. you are building a bill of materials (somewhere). that bom needs the quantity of each direct item that has been added, and any follow-on/sub-items that are the result of each item, recursively down to the end of the chain. from a processing point of view, just do things once, when an input is added/deleted/changed, and only for those things that are in the bom. this approach would be the same as an onchange event in a browser or a trigger in a database. some input event occurs, the code that runs, takes the rules that have been defined for that event and applies them as needed. if a window gets added/deleted, the rules defined for that window type tell the code what and what quantity of sub-items (such as the corner molding) need to be added/deleted from the bom, any of those sub-items will have rules that tell the code what and what quantity of sub-sub-items (such as fasteners) need to be added/deleted from the bom. the array structure you have for the overallQuantities already has an array of arrays for each productId, though it looks like the code isn't using more than the first element of each array. the suggested usage of the [main_item_id] as the secondary array index, in reply #6, keeps each element in the array tied to what caused that quantity. if you change the quantity of the parent (delete a specific size window), you only have to calculate and update that corresponding one element for the child item (corner molding.) all the other quantities of that particular child item aren't touched. because you have more than just two levels, what i posted in reply #6 would actually be recursive, and look like the following with as many levels as needed - overallQuantities[main_item_id] = quantity overallQuantities[sub_item_id][main_item_id] = quantity overallQuantities[sub_sub_item_id][sub_item_id][main_item_id] = quantity for the insulated vs uninsulated pricing, i would maintain two boms, one for each case. the code would calculate quantities with and without insulation and store the results in separate boms (actually, i would just use an array with a main index that indicates insulated and uninsulated branches.) for the _calc() function in my example. you can make as many different functions that you need for the different classes of rules. just call the correct one depending on the situation. in the list of rules, you can 'dynamically' call you own functions, using variable functions, by listing the function name somewhere in the rules. in my example, i am calling the ceil function using variable functions. your rule(s) could have function name, like i used, or even an array of function names that you loop over to dynamically call each function in turn.
  14. yes, it is. and, yes, it is. it's testing the result of the assignment statement, which will be the value that was assigned. when there are no more rows, the fetch statement returns a false, which will be assigned to the $x variable, and the value tested for the loop condition will be a false and the loop will end. from the documentation for the assignment operator -
  15. we understand what you are doing and how you are doing it. the problem is, your current code is taking a long time to run and all the hard-coded logic and hard-code properties in the code are a maintenance problem. from what i gather, to recalculate the bom/price, upon each change being input, you are currently calling the code for every possible building productId (~300 times), to get each id to calculate how much of it is needed based on the quantity of what it is used for. this also requires that you call the code with the product id's in the proper order. for example, if you haven't called the code to update the cornerMoulding quantity yet, any product id that is used for cornerMoulding, such as fasteners, won't produce the correct quantity. this is what i would call a bottom-up approach. my suggestion earlier in the thread is a top-down approach, where each change only causes the items affected by that change to be recalculated. for the performance problem, if the function method produced acceptable performance, you would want to continue using that method. for the code maintenance problem (top-down or bottom-up approach), you need a data driven design, where you define the rules in a data structure (an array for now, a database table later) that tells the code what to do. for the information you have shown in this thread (bottom-up approach), the following pseudo/non-functional code demonstrates a data driven design - // define the rules that tell the code what to do $items = array(); $items[] = array(threeByThreeFixedWindow,1.5); // id, individual multiplier $items[] = array(fourByThreeFixedWindow,1.5); // id, individual multiplier $items[] = array(threeFootStandardDoor,2.5); // id, individual multiplier $rules[cornerMoulding] = array($items,1,'ceil'); // array of item(s), group multiplier, operator $items = array(); $items[] = array(smokeStop,1); // id, individual multiplier $items[] = array(fireStop,1); // id, individual multiplier $rules[smokeDamper] = array($items, 3,'ceil'); // array of item(s), group multiplier, operator $items = array(); $items[] = array(poly,1); // id, individual multiplier $rules[tuckTape] = array($items, 1/2000, 'ceil'); // array of item(s), group multiplier, operator // a function that knows how to apply the rules function _calc($rule){ $qty = 0; foreach($rule[0] as $item){ $qty += $this->getTotalQuantityBuildingProduct($item[0], $showInsulation, $showPerma) * $item[1]; // get the total for the productId and apply the individual multiplier } $qty *= $rule[1]; // apply group multiplier if($rule[2] == ''){ return $qty; } else { return $rule[2]($qty); // use variable functions to apply the operator } } // example usage - $quantities[] = _calc($rules[smokeDamper]); // call this to use the defined $rules for the productId, instead of the hard-code program logic
  16. your code that's not commented out, that's using the $data values, is after the end of the while(){} loop. at that point, $data is a FALSE value. there is no $data[0], ... for the code to use. you should be getting 'undefined offset...' php error messages. also, the code inside your while(){} loop is never incrementing $row, so the code inside the loop, will skip every row.
  17. and again - just posting that you cannot get something to work is pointless, because we are not going to write or fix your code for you. also, the link i posted above in this thread HIGHLIGHTS the http_build_query() statements in the code, you cannot miss where they are being used at in the code.
  18. i've been looking at your code posted in this thread, and it appears that the rules in the code are for calculating the amount of a sub-item by getting the quantity of each relevant main item that uses that sub-item and putting that quantity through the rule in this code. also, despite storing the quantity for each productId as an array within the main array, the code in this thread is only storing ONE array element, with the total quantity. this means you are calling the getQuantityBuildingProduct() function for each sub-item that a main item uses, each time the main item quantity gets changed (unless you are calling the function for EVERY POSSIBLE sub-item, every time ANY main item quantity changes, in which case i can see why this would take 10 seconds). this requires that the code (or data) for each main item contain a list of sub-items and your code in this thread requires the correct rule for each sub-item. so, you have two separate places in the code that must be kept up to date with any new or changed relationship between main and sub-items. i suggest, instead, just using the list of sub-items, located in the main item code (or data), to call the appropriate rule for each sub-item and update the sub-item quantity at the time you update a main item quantity. you are storing data like this - overallQuantities[main_item_id][] = quantity // main items overallQuantities[sub_item_id][] = quantity // sub items if you add the main_item_id as an array index for the sub-items, you can find and update the corresponding quantity of a sub-item when the quantity of the main item changes - overallQuantities[sub_item_id][main_item_id] = quantity for example - overallQuantities[cornerMoulding][threeByThreeFixedWindow] = x quantity overallQuantities[cornerMoulding][threeFootStandardDoor] = y quantity your getTotalQuantityBuildingProduct() function will work with this structure (it's actually getting a single element array now, but would be getting an array of arrays, if a sub-item is used with more than one main item.) you can also replace the foreach() loop in the getTotalQuantityBuildingProduct() function with an array_sum() call, both with your current scheme and with the one i have suggested. this will also allow you to produce a cross-reference listing of the sub-items showing what amount of them are used for each different main item - cornerMoulding - threeByThreeFixedWindow - x quantity threeFootStandardDoor - y quantity edit: and in thinking about your use of the $this->overallQuantities[$productId] array to cache the amounts, if you change a quantity of a main item, i.e. the number of a type of window, your code won't recalculate the amount of a sub-item, i.e. the corner molding, if the sub-item amount is already in the array, which it likely would be, unless you have even more code that we haven't seen to take care of this common occrance.
  19. you would need to check the mail server's logs to find out what is actually happening. it is either deciding not to send them (usually due to relaying restrictions combined with what the to: and from: email addresses are) or the receiving mail server is refusing them or deciding not to process them (if they are invalid or the receiving mail server cannot confirm that your mail server is authorized to send email from where the mails stay they are from), or the receiving mail server is considering them spam/junk and is placing them into the junk mail folder of the recipient. if the mail server is returning an error to php, the mail() function should returning a false value that you can test for. if the mail server is returning error information to php, you can either echo or log the php errors to find out more information. are you sending an email to yourself, i.e. a mail box at your mail server or are you trying to send the emails through your mail server to other/external mail servers? also, in the cases where it doesn't work, what sort of error or symptom are you getting?
  20. what was the performance of your code when using functions (i'll assume you were calling the appropriate function dynamically using variable functions?)? using a class->property as the case x: value, is not going to be as efficient as using a fixed value. i would use a defined constant as the case values. the same would be true for all the other class->properties you are showing in the code. you have essentially created a different variable/property, who's name indicates the purpose of the variable, when in fact nothing about the usage is variable.
  21. the problem seems to be because the ?msg=x that you are putting into your links are only putting an x value from the original message, not the replies.
  22. your raiz/root column only has to do with displaying a list of the original message and the replies that belong with that message. it doesn't have anything to do with displaying a specific message or marking a message as being read. displaying a specific message or marking a message as being read only involves the id of that specific message. the only people who can view any specific message are the sender or the recipient. your first query should enforce that condition - $result = mysqli_query($con, "SELECT * FROM message WHERE id = $message AND (`to` = $utilizador OR `from` = $utilizador)"); the update query, which in your last post above didn't correct the php logic to use a == comparison, should be - if($utilizador == $ln['to']){ $update= "UPDATE messages SET `read` = 1 WHERE id = $message"; mysqli_query($con, $update); } note: read is a reserved mysql keyword (along with from and to in the first query) and must be enclosed in back-ticks `` to prevent mysql errors. you would be getting a mysql error from your update query. your code needs to ALWAYS have error checking logic in it, to get your code to tell you when, where, and why something is failing. lastly, the $_GET['msg']/$message are external data and can be anything. you MUST validate that they are of the expected format and you must protect against sql injection. the best way of protecting against sql injection is to use prepared queries. for what you are using the value for in your code, someone could inject sql that allows them to display ANY message that belongs to anyone. which defeats the point of a Private Message system.
  23. the following forum post addresses much of what you should be doing in your code - http://forums.phpfreaks.com/topic/296742-hello-pretty-simple-php-form-i-broke-itplease-assist/?hl=%2Bsending&do=findComment&comment=1513725 pay particular attention to item #8 (the smiley) about the From: email header. edit: i also notice that you have $POST used in some of your code. it's $_POST. if you had php's error_reporting set to E_ALL and display_errors set to ON, you would be getting undefined error messages alerting you to the incorrect variable names.
  24. if your free web host doesn't provide sending/outgoing email, then the person you know that is able to send/receive contact form emails is likely sending the email through or just to some other mail server, such as a gmail account. if your web host hasn't blocked communications on port 25, you can, using a script like phpmailer, send emails to your own personal email account, hosted somewhere else. to do this, you must use smtp authentication (supplying your email account's email address and password) with the phpmailer script. there are examples at the phpmailer 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.