Jump to content

Leaderboard

Popular Content

Showing content with the highest reputation since 07/01/2021 in all areas

  1. less... $matched = array_intersect_key($all, array_flip($referred_by_Affiliate));
    2 points
  2. Ya, really doable. Like you got told a bunch of times in the past, same junk about db's, locations, whatver. C'mon its been at least 5 yrs that youve been asking this same thing just worded different. Prolly want to check the gazillion other places youve asked this same junk over the past years too.
    1 point
  3. PS It would better to change line 6 above to $sku['products'][$id][$k] = $v;
    1 point
  4. 1 point
  5. It's been at least a decade since I played around with the getid3 library. I'll be honest, I have no idea what ETCO tag data is. But, I have a possible solution. Do you have a file with existing ETCO tags or is there a tag editing application that you can use to set such tags? If you have a file with example tag data that you know what it represents, then instead of using getid3 to set the data, use it to get the data. You can then see what the format of the data is that it expects. I remember doing something similar for some other tag information at the time.
    1 point
  6. I would ... foreach ($array as $k => $v) { $id = substr($k, -5); if (ctype_digit($id)) { $len = strlen($k); $k = substr($k, 0, $len-5); $sku[$id][$k] = $v; } else $sku[$k] = $v; } echo '<pre>' . print_r($sku, 1) . '</pre>'; giving... Array ( [77777] => Array ( [newQuantity] => 3 [newPrice] => 5 [usedQuantity] => 1 [usedPrice] => 3.99 [total] => 18.99 ) [88888] => Array ( [newQuantity] => 0 [newPrice] => 0 [usedQuantity] => 4 [usedPrice] => 12 [total] => 48 ) [44444] => Array ( [newQuantity] => 2 [newPrice] => 4 [usedQuantity] => 0 [usedPrice] => 3.99 [total] => 8 ) [date] => July 25 2021 [address] => 123 Anystreet Avenue [address2] => [zipcode] => 90210 [city] => Beverly Hills [state] => CA [planet] => Mars )
    1 point
  7. After you json_decode without the true do the following: echo "<pre>"; print_r($result); echo "</pre>"; That will show you the resulting associative array so you can see how to reference the elements by key.
    1 point
  8. Here's a shortened version. It also uses json_decode without the "true" to give an object (containing objects) $all = json_decode($all_items_sold); $placeholders = $values = []; foreach ($all as $pid => $prod){ if (in_array($pid, $referred_by_Affiliate)) { $placeholders[] = "(?,?,?)"; array_push($values, $pid, $prod->item, $prod->price); } } $stmt = $db->prepare("INSERT INTO mytable (prod_id, item, price) VALUES " . join(',', $placeholders)); $stmt->execute($values); A PHP join has nothing to do with MySQL joins.
    1 point
  9. Every time you need a new format you'll have to modify your table schema. That's not a good thing. There is no exhaustive list of formats you can rely on, which means you are coming up with this list on your own and deciding "yeah, I think that's all of them". That's not a good thing. If there's 20 different media formats then you've got an ENUM with 20 different entries. That's not a good thing. It's the same problem as you had with the list of genres.
    1 point
  10. you CAN configure the web server to treat .html (or any other extension) as a php file. the default is for only the .php extension.
    1 point
  11. UPDATE / DELETE queries don't have a result set, as such mysqli_query will just return true/false to indicate whether the query was successful or not. There's nothing to fetch so no reason to use mysqli_fetch_array. By returning the result, I mean those methods could have just been: public function deleteCategory($id) { return mysqli_query($this->conn, "DELETE FROM top_categories WHERE top_cat_id=$id"); } mysqli_query will return true or false. Adding the variable and if branch to check if it's true, just to then return true if it is, is entirely unnecessary.
    1 point
  12. Your file should be named with a .php extension, not .html. You need to load the file via the web server, not by just double-clicking on it to open it in windows. Open your browser and load the url http://localhost/index.php
    1 point
  13. Your file name is index.html and not index.php. You need a php file for php code to be executed.
    1 point
  14. Do yourself a favor and use PHPMailer - it's far easier and more robust than PHP's native mail() function. It also has great debugging output.
    1 point
  15. It's a prepared statement, hence the prepare() method called on the $connection object. It's the correct way to run a query in PHP these days, so well done! In the SQL statement passed to the prepare() method, the `:username`, `:emailbox`, and `:passwordbox` are placeholders in the query. When you pass an array to execute(), that array contains the values to use in those placeholders, so the ':username', ':emailbox', and ':passwordbox' there are keys for the array so that SQL knows which value to plug in to each placeholder. Basically, using prepared statements blocks a potential avenue that hackers can use to attack your database or get your data. There are other benefits to prepared statements, but that's kind of the biggest and more pertinent for most systems.
    1 point
  16. Don't know either. I saw this a while back myself too and assumed that IPB would fix it themselves at some point, but obviously they have not. Looking at the template, it seems like the MFA screens were designed before a recent theme overhaul. Namely, they use a "ipsModal" CSS scheme when it seems they need to move to "ipsDialog". It's also missing out on color changes as the popup on dark theme isn't using the correct background colors (but it's still fine). I've made that change for the authentication popup: it's still rather wide but I think it's definitely better now.
    1 point
  17. Clearly they were wrong because you did what they said and it didn't work. flex and flex-direction only affect the element's children, not all its descendants too.
    1 point
  18. the code on a page should be laid out in this general order (yes there are exceptions) - initialization post method from processing code (the current problem you are having with a redirect) get method business logic - code that knows how to get/produce the data/content needed for the dynamic portions of the page html document
    1 point
  19. What "command" to do what?
    1 point
  20. You do essentially what you were doing with $dbHandler. You had the right idea, just the wrong details. private static $instance = null; //... public static function getInstance() { if(self::$instance) { return self::$instance; } return self::$instance = new Self(); }
    1 point
  21. If they have root access then there is nothing you can do. No amount of encryption can save you from that.
    1 point
  22. $product_stock, $product_status and $product_id are all nemeric so do not put them in side quotes within your query string. Any extra whitespace will prevent a match. It is more efficient to prepare a query once and bind the parameters then execute it within the loop. You are doing it the slowest way possible. However, the most efficient way would be to put the data in array then use a single multi-record insert. $fp = fopen('myfile.csv', 'r'); $rec = fgetcsv($fp); // header rec while ($rec = fgetcsv($fp)) { $data[] = vsprintf("(%d, %d)", $rec); // store in array } // now insert/update the array data into the table $conn->query("INSERT INTO products (id, product_stock) VALUES " . join(',', $data) . " ON DUPLICATE KEY UPDATE product_stock = VALUES(product_stock) , product_status = 1 ");
    1 point
  23. Hmm! Method A or method B? When you are caught on the horns of a dilemma, look for a third way Consider a sticky registration form. When first loaded the input values are blank, but if the validation fails you want to show the user's values. In this situation I like the "null coalesce" operator, ie "??". Example <?php $fname = $_POST['fname'] ?? ''; $lname = $_POST['lname'] ?? ''; $email = $_POST['email'] ?? ''; $mobile = $_POST['mobile'] ?? ''; $error_message = ''; if ($_SERVER['REQUEST_METHOD']=='POST') { $errors = []; // array for any error messages // validate input here if (!$errors) { // update database here header("location: thispage.php"); // reload page exit; } else { $error_message = 'yada yada'; } } ?> <html> <body> <form method='POST'> First name : <input type='text' name='fname' value='<?=$fname?>'> <br> Last name : <input type='text' name='lname' value='<?=$lname?>'> <br> Email : <input type='text' name='email' value='<?=$email?>'> <br> Mobile : <input type='text' name='mobile' value='<?=$mobile?>'> <br> <br> <button type='submit'>Submit</button> </form> <?=$error_message?> </body> </html>
    1 point
  24. both_tables is just the name of the virtual-table created by the two inner select queries. A name is necessary there, but it doesn't have to be both_tables, that's just a descriptive name. You can use a different name if you wanted.
    1 point
  25. Yeah! I have tried who.is but after some searches, it asks for payment. I need free one.
    1 point
  26. Using attempted = [5,6] with the code I posted, I get... <ul id="list"> <li class="pagination-link" id="1">1</li> <li class="pagination-link" id="2">2</li> <li class="pagination-link" id="3">3</li> <li class="pagination-link" id="4">4</li> <li class="pagination-link is-current" id="5">5</li> <li class="pagination-link is-current" id="6">6</li> </ul>
    1 point
  27. If you just want the print-r() output (???) then '</td><td> <a href="">' . print_r($value->users, true) . "</a></td></tr>";
    1 point
  28. From the Laravel documentation: $flight->name = 'Paris to London'; $flight->save(); From your code: $data->image=$request->image; $data->save; Do you see the difference?
    1 point
  29. What is "->save", exactly? Try telling me in as much detail as you possibly can what that line is supposed to do. Lots of detail. Like you had to explain it to someone who is new to programming and has very little understanding of how things work.
    1 point
  30. 1 point
  31. You know your application and framework (looks like Laravel) better than us so it's not like we can instantly tell you what table and/or column(s) you have to update. If there's a "last logged in" timestamp on the user table then update that. Otherwise...
    1 point
  32. Passwords should be stored securely in a database (MySQL).
    1 point
  33. That is calling the execute() a second time. If username or email must be unique that could be generating a duplicate key error - check mysql error, don't just assume it's a connection error. Better still, put this line directly before your mysqli_connect() line mysqli_report(MYSQLI_REPORT_ERROR|MYSQLI_REPORT_STRICT); the all errors will throw a notification without all those if()s
    1 point
  34. You could use a loop. For example, $mcptitles = array("Volvo", "BMW", "Toyota"); foreach($mcptitles as $mcptitle) { //your existing code here... } Note that I changed the name of variable that holds the array. That way it should hopefully work with your existing code. Also note that I didn't review your code since it sounds like it's working.
    1 point
  35. Just for fun ... echo ad_decimo('XIIX'); // 18 (used by Roman 18th legion) echo ad_decimo('MCMIL'); // 1949 echo ad_decimo('MCMXLIX'); // 1949 function ad_decimo($str) { $M = 1000; $D = 500; $C = 100; $L = 50; $X = 10; $V = 5; $I = 1; foreach (str_split(strtoupper($str)) as $r) { if (!isset($$r)) return 0; $ra[] = [ 'r' => $r, 'v' => $$r ]; } $d = 0; foreach ($ra as $p => $a) { $d += $a['v'] * subtracto($ra, $p, $a['v']); } return $d; } function subtracto($rarr, $pos, $val) { // is there a higher value letter following this one? for($i=$pos+1, $k=count($rarr); $i<$k; $i++) { if ($rarr[$i]['v'] > $val) return -1; } return 1; }
    1 point
  36. Here's my attempt DATA mysql> select * from ajoo -> order by user, recno; +-------+----------+---------+---------+ | recno | user | v_score | rollavg | +-------+----------+---------+---------+ | 6 | mina1111 | 4 | 3.2500 | | 7 | mina1111 | 3 | 3.2000 | | 8 | mina1111 | 2 | 3.2000 | | 9 | mina1111 | 4 | 3.4000 | | 10 | mina1111 | 5 | 3.6000 | | 11 | mina1111 | 0 | 2.8000 | | 12 | mina1111 | 1 | 2.5000 | | 13 | mina1111 | 1 | 1.7500 | | 14 | mina1111 | 1 | 0.7500 | | 1 | nina1234 | 3 | NULL | | 4 | nina1234 | 3 | 2.5000 | | 5 | nina1234 | 4 | 3.0000 | | 15 | nina1234 | 5 | NULL | | 17 | nina1234 | 2 | 2.0000 | | 22 | nina1234 | 2 | NULL | +-------+----------+---------+---------+ QUERIES -- -- create temp table a -- CREATE TEMPORARY TABLE temp_a SELECT a.recno , a.v_score , @count := CASE WHEN user = @prevu THEN @count+1 ELSE 1 END AS reccount , @prevu := user AS user FROM ajoo a JOIN (SELECT @count:=0, @prevu:=NULL) AS init ORDER BY user, recno ; -- -- create temp table b -- (copy of temp_a) -- CREATE TEMPORARY TABLE temp_b SELECT * FROM temp_a ; -- -- get results -- SELECT av.user , avg5 , tot3 FROM ( SELECT user , AVG(v_score) as avg5 FROM ( SELECT a.user , v_score FROM temp_a a JOIN ( SELECT user , COUNT(*) AS maxrec FROM ajoo GROUP BY user ) max ON a.user = max.user AND a.reccount > max.maxrec - 5 ) tots GROUP BY user ) av JOIN ( SELECT user , SUM(v_score) as tot3 FROM ( SELECT b.user , v_score FROM temp_b b JOIN ( SELECT user , COUNT(*) AS maxrec FROM ajoo GROUP BY user ) max ON b.user = max.user AND b.reccount > max.maxrec - 3 ) tots GROUP BY user ) tot USING (user) ; RESULTS +----------+--------+------+ | user | avg5 | tot3 | +----------+--------+------+ | mina1111 | 1.6000 | 3 | | nina1234 | 3.2000 | 9 | +----------+--------+------+
    1 point
  37. There is a very easy way to do this using a MySql myisam table. Store each vote in a table like this... CREATE TABLE `vote` ( `username` varchar(50) NOT NULL, `vote_year` year(4) NOT NULL, `week_num` tinyint(4) NOT NULL, `vote_count` int(11) NOT NULL AUTO_INCREMENT, `time_voted` datetime DEFAULT CURRENT_TIMESTAMP, `voted_for` int(11) DEFAULT NULL COMMENT 'Who/whatever was voted for', PRIMARY KEY (`username`,`vote_year`,`week_num`,`vote_count`) ) ENGINE=MyISAM DEFAULT CHARSET=utf8; Note the last column of the primary key is the auto-increment column "vote_count". This will make the vote count start again at 1 for each username each week whe you add votes. mysql> INSERT INTO vote (username, vote_year, week_num, voted_for) VALUES -> ('user1', year(curdate()), weekofyear(curdate()), 1), -> ('user1', year(curdate()), weekofyear(curdate()), 20), -> ('user1', year(curdate()), weekofyear(curdate()), 5), -> ('user2', year(curdate()), weekofyear(curdate()), 5), -> ('user2', year(curdate()), weekofyear(curdate()), 1), -> ('user2', year(curdate()), weekofyear(curdate()), 3); Query OK, 6 rows affected (0.00 sec) mysql> select * from vote; +----------+-----------+----------+------------+---------------------+-----------+ | username | vote_year | week_num | vote_count | time_voted | voted_for | +----------+-----------+----------+------------+---------------------+-----------+ | user1 | 2021 | 24 | 1 | 2021-06-16 17:37:56 | 1 | | user1 | 2021 | 24 | 2 | 2021-06-16 17:37:56 | 20 | | user1 | 2021 | 24 | 3 | 2021-06-16 17:37:56 | 5 | | user2 | 2021 | 24 | 1 | 2021-06-16 17:37:56 | 5 | | user2 | 2021 | 24 | 2 | 2021-06-16 17:37:56 | 1 | | user2 | 2021 | 24 | 3 | 2021-06-16 17:37:56 | 3 | +----------+-----------+----------+------------+---------------------+-----------+ 6 rows in set (0.00 sec) To do the insert in PHP $stmt = $pdo->prepare("INSERT INTO vote (username, vote_year, week_num, voted_for) VALUES ( ?, year(curdate()), weekofyear(curdate()), ? ) "); $stmt->execute( [ $username, $votedFor ] ); Now it doesn't matter how many times a user votes. When you come to counting the votes for each "voted_for" just ignore all records whose vote_count is > 10 SELECT voted_for , count(*) as votes FROM vote WHERE vote_count <= 10 GROUP BY voted_for ORDER BY votes DESC
    1 point
  38. @indie I know I'm coming fairly late, but here is your Regex: \[sharedmedia=core:attachments:(\d+)\] https://rubular.com/r/fOGRTK3l3LcLx1
    1 point
  39. Here's my function for ordinal suffices function ordSuffix($n) { $str = "$n"; $t = $n > 9 ? substr($str,-2,1) : 0; $u = substr($str,-1); if ($t==1) return $str . 'th'; else switch ($u) { case 1: return $str . 'st'; case 2: return $str . 'nd'; case 3: return $str . 'rd'; default: return $str . 'th'; } } echo ordSuffix(1).'<br>'; // 1st echo ordSuffix(11).'<br>'; // 11th echo ordSuffix(101).'<br>'; // 101st echo ordSuffix(2).'<br>'; // 2nd echo ordSuffix(3).'<br>'; // 3rd echo ordSuffix(8).'<br>'; // 8th
    1 point
  40. Try this SELECT yearid , semesterid , subjectid , regno , rank , total , grade , comment FROM ( SELECT yearid , semesterid , subjectid , @seq := CASE WHEN yss <> @prev THEN 1 ELSE @seq + 1 END as seq , @rank := CASE WHEN total = @prevtot THEN @rank ELSE @seq END as rank , @prevtot := total as total , @prev := yss as yss , regno FROM ( SELECT yearid , semesterid , subjectid , concat(yearid, semesterid, subjectid) as yss , regno , total FROM subject_position ORDER BY yearid, semesterid, subjectid, total DESC -- LIMIT 18446744073709551615 -- MariaDB requires this line uncommented * ) sorted JOIN (SELECT @prev := '', @seq := 0, @rank := 0, @prevtot := 0) as init ) ranked JOIN grade ON total BETWEEN grade.lomark AND grade.himark; (I invented my own grades) mysql> select * from grade; +----+-------+--------+--------+-------------+ | id | grade | lomark | himark | comment | +----+-------+--------+--------+-------------+ | 1 | A* | 91 | 100 | Distinction | | 2 | A | 80 | 90 | Excellent | | 3 | B1 | 75 | 79 | V Good | | 4 | B2 | 70 | 74 | V Good | | 5 | C1 | 68 | 69 | Good | | 6 | C2 | 66 | 67 | Good | | 7 | C3 | 64 | 65 | Good | | 8 | C4 | 61 | 63 | Good | | 9 | D1 | 59 | 60 | Pass | | 10 | D2 | 57 | 58 | Pass | | 11 | D3 | 55 | 56 | Pass | | 12 | D4 | 53 | 54 | Pass | | 13 | D5 | 51 | 52 | Pass | | 14 | D6 | 49 | 50 | Pass | | 15 | D7 | 40 | 48 | Pass | | 16 | E | 21 | 39 | Poor | | 17 | F | 0 | 20 | Fail | +----+-------+--------+--------+-------------+ Query results... +--------+------------+-----------+-------+------+-------+-------+-------------+ | yearid | semesterid | subjectid | regno | rank | total | grade | comment | +--------+------------+-----------+-------+------+-------+-------+-------------+ | 1 | 1 | 1 | 6073 | 1 | 73 | B2 | V Good | | 1 | 1 | 1 | 4663 | 2 | 72 | B2 | V Good | | 1 | 1 | 2 | 6073 | 1 | 61 | C4 | Good | | 1 | 1 | 2 | 4663 | 2 | 47 | D7 | Pass | | 1 | 1 | 3 | 4663 | 1 | 82 | A | Excellent | | 1 | 1 | 3 | 6073 | 2 | 61 | C4 | Good | | 1 | 1 | 4 | 4663 | 1 | 99 | A* | Distinction | | 1 | 1 | 4 | 6073 | 2 | 95 | A* | Distinction | | 1 | 1 | 5 | 6073 | 1 | 100 | A* | Distinction | | 1 | 1 | 5 | 4663 | 2 | 70 | B2 | V Good | | 1 | 1 | 6 | 4663 | 1 | 69 | C1 | Good | | 1 | 1 | 6 | 6073 | 2 | 67 | C2 | Good | | 1 | 1 | 7 | 6073 | 1 | 80 | A | Excellent | | 1 | 1 | 7 | 4663 | 2 | 77 | B1 | V Good | | 1 | 1 | 8 | 6073 | 2 | 77 | B1 | V Good | | 1 | 1 | 8 | 4663 | 2 | 58 | D2 | Pass | | 1 | 1 | 9 | 4663 | 1 | 96 | A* | Distinction | | 1 | 1 | 9 | 6073 | 1 | 96 | A* | Distinction | | 1 | 1 | 10 | 4663 | 1 | 78 | B1 | V Good | | 1 | 1 | 10 | 6073 | 2 | 77 | B1 | V Good | | 1 | 1 | 11 | 6073 | 1 | 88 | A | Excellent | | 1 | 1 | 11 | 4663 | 2 | 48 | D7 | Pass | | 1 | 1 | 12 | 6073 | 1 | 94 | A* | Distinction | | 1 | 1 | 12 | 4663 | 2 | 69 | C1 | Good | | 1 | 2 | 1 | 6073 | 1 | 70 | B2 | V Good | | 1 | 2 | 1 | 4663 | 2 | 28 | E | Poor | | 1 | 2 | 2 | 4663 | 1 | 68 | C1 | Good | | 1 | 2 | 2 | 6073 | 2 | 59 | D1 | Pass | | 1 | 2 | 3 | 6073 | 1 | 70 | B2 | V Good | | 1 | 2 | 3 | 4663 | 2 | 68 | C1 | Good | | 1 | 2 | 4 | 4663 | 1 | 81 | A | Excellent | | 1 | 2 | 4 | 6073 | 2 | 72 | B2 | V Good | | 1 | 2 | 5 | 4663 | 1 | 84 | A | Excellent | | 1 | 2 | 5 | 6073 | 2 | 72 | B2 | V Good | | 1 | 2 | 6 | 6073 | 2 | 72 | B2 | V Good | | 1 | 2 | 6 | 4663 | 2 | 58 | D2 | Pass | | 1 | 2 | 7 | 4663 | 1 | 71 | B2 | V Good | | 1 | 2 | 7 | 6073 | 2 | 70 | B2 | V Good | | 1 | 2 | 8 | 6073 | 1 | 55 | D3 | Pass | | 1 | 2 | 8 | 4663 | 2 | 48 | D7 | Pass | | 1 | 2 | 9 | 4663 | 1 | 66 | C2 | Good | | 1 | 2 | 9 | 6073 | 2 | 51 | D5 | Pass | | 1 | 2 | 10 | 6073 | 1 | 58 | D2 | Pass | | 1 | 2 | 10 | 4663 | 2 | 37 | E | Poor | | 1 | 2 | 11 | 6073 | 1 | 59 | D1 | Pass | | 1 | 2 | 11 | 4663 | 2 | 57 | D2 | Pass | | 1 | 2 | 12 | 6073 | 1 | 69 | C1 | Good | | 1 | 2 | 12 | 4663 | 2 | 67 | C2 | Good | | 1 | 3 | 1 | 4663 | 1 | 94 | A* | Distinction | | 1 | 3 | 1 | 6073 | 2 | 82 | A | Excellent | | 1 | 3 | 2 | 6073 | 1 | 76 | B1 | V Good | | 1 | 3 | 2 | 4663 | 2 | 69 | C1 | Good | | 1 | 3 | 3 | 6073 | 1 | 81 | A | Excellent | | 1 | 3 | 3 | 4663 | 2 | 63 | C4 | Good | | 1 | 3 | 4 | 4663 | 1 | 81 | A | Excellent | | 1 | 3 | 4 | 6073 | 2 | 77 | B1 | V Good | | 1 | 3 | 5 | 6073 | 1 | 83 | A | Excellent | | 1 | 3 | 5 | 4663 | 2 | 72 | B2 | V Good | | 1 | 3 | 6 | 6073 | 1 | 83 | A | Excellent | | 1 | 3 | 6 | 4663 | 2 | 78 | B1 | V Good | | 1 | 3 | 7 | 4663 | 1 | 77 | B1 | V Good | | 1 | 3 | 7 | 6073 | 2 | 75 | B1 | V Good | | 1 | 3 | 8 | 6073 | 1 | 82 | A | Excellent | | 1 | 3 | 8 | 4663 | 2 | 74 | B2 | V Good | | 1 | 3 | 9 | 6073 | 1 | 95 | A* | Distinction | | 1 | 3 | 9 | 4663 | 2 | 56 | D3 | Pass | | 1 | 3 | 10 | 4663 | 1 | 87 | A | Excellent | | 1 | 3 | 10 | 6073 | 2 | 79 | B1 | V Good | | 1 | 3 | 11 | 6073 | 1 | 71 | B2 | V Good | | 1 | 3 | 11 | 4663 | 2 | 70 | B2 | V Good | | 1 | 3 | 12 | 6073 | 1 | 90 | A | Excellent | | 1 | 3 | 12 | 4663 | 2 | 82 | A | Excellent | +--------+------------+-----------+-------+------+-------+-------+-------------+ [edit] * The idiots at Maria maintain that as the subquery effectively creates a table, and tables are inherently unordered, then the ORDER BY clause should be ignored. The rest of the world think this is a resultset and there can be ordered. The LIMIT 264-1 forces it to use an ordered temporary table.
    1 point
This leaderboard is set to New York/GMT-04:00
  • Newsletter

    Want to keep up to date with all our latest news and information?
    Sign Up
×
×
  • 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.