Register a SA Forums Account here!
JOINING THE SA FORUMS WILL REMOVE THIS BIG AD, THE ANNOYING UNDERLINED ADS, AND STUPID INTERSTITIAL ADS!!!

You can: log in, read the tech support FAQ, or request your lost password. This dumb message (and those ads) will appear on every screen until you register! Get rid of this crap by registering your own SA Forums Account and joining roughly 150,000 Goons, for the one-time price of $9.95! We charge money because it costs us money per month for bills, and since we don't believe in showing ads to our users, we try to make the money back through forum registrations.
 
  • Post
  • Reply
musclecoder
Oct 23, 2006

I'm all about meeting girls. I'm all about meeting guys.

IcedPee posted:

I hope this is the right thread for this.

I'm completely new to PHP. I've done plenty of C/C++/C# and a fair amount of ASP.NET and MVC, etc etc, and I got roped into working on a project with PHP and MySQL. I'm from an almost exclusively Microsoft background, and the hosting we're using is a LAMP stack. I'm setting up a testing environment to run through a few tutorials on my computers at home, and my question is this: should I bother setting up Apache on my Win7 box, or should I just configure PHP and MySql to work through IIS? Would the experience of using Apache on a Win7 box help at all when our hosting is all Linux, or has cross-platform publishing finally gotten painless?

I think a better answer would be neither. Both of those sound like a huge pain in the rear end. What I think you should do is use Vagrant to set up a Linux VM with Ubuntu/Debian and install a LAMP stack on there.

I wrote a post a while ago on how to get started with Vagrant: https://leftnode.com/entry/getting-started-with-vagrant.html

It uses Postgres but you can replace it to use MySQL. I'm also writing a book about all of this and PHP deployments, PM me if you're interested or need more help with Vagrant. It really is a great piece of software, has totally changed how we develop at work.

Because your Vagrant VM is literally a Linux box, you can make it identical to your production server as well. I prefer to use the built in PHP server for development, but you're welcome to customize the bootstrap script to use Apache/Nginx (use Nginx).

Edit: Or like what Sulla-Marius 88 said, you can also rent a small server to play around with. I don't love Digital Ocean for production apps, but for $5/mo they're great for messing around on.

Adbot
ADBOT LOVES YOU

IcedPee
Jan 11, 2008

Yarrrr! I be here to plunder the fun outta me workplace! Avast!

FREE DECAHEDRON!
Thanks for the responses.

For starters, I'm not working with any commercial products or anything like that - I need to store some stuff in the database and display it on a page in a timeline fashion. I don't foresee it being a very big deal.

As far as setting up a VM with Linux on it.... I believe I have what my old boss would call a, "violent, negative reaction." I've had nothing but horrible experiences trying (and never once succeeding, btw) to run Linux in a dual-boot or even VM setting on any of my machines at home. I really really don't want to do that for something this simple unless it really is the best option (PHP for IIS looks to be a simple install, which is an attractive option for just mucking through tutorials).

Granted, this was years ago and it's probably not as bad as it used to be.

If setting up a VM really is the way to go, are there any frameworks I should be looking at that make doing simple CRUD operations safer for an absolute PHP beginner? I've heard the horror stores and don't want to be in one.

Edit: Oh, I guess I'm gonna have to do user accounts and eventually PayPal for transactions, too. I forgot about that.

IcedPee fucked around with this message at 17:18 on Nov 7, 2013

DaTroof
Nov 16, 2000

CC LIMERICK CONTEST GRAND CHAMPION
There once was a poster named Troof
Who was getting quite long in the toof

IcedPee posted:

I don't foresee it being a very big deal.

[...]

Edit: Oh, I guess I'm gonna have to do user accounts and eventually PayPal for transactions, too. I forgot about that.

This seems... familiar. And not in a good way

You're best off mirroring your production environment as closely as possible. If it's a LAMP, set up a LAMP for development. A WAMP might come close enough, but you'll probably run into platform exceptions every now and then.

If you're a big fan of unnecessary cross-platform debugging against a unique production environment and endless futility headaches, go ahead and use IIS.

Calyn
Sep 3, 2011
Using Vagrant/PuPHPet, installing LAMP on a virtual machine on your windows box should be quite easy and will more closely match your production environment. The instructions on https://puphpet.com/ are quite straight-forward. Otherwise just from a really quick google search, this tutorial came up: http://www.dev-metal.com/setup-virtual-machine-multiple-vagrant-puphpet/ - might be useful, or else there should be tons of other tutorials on the same topic out there.

If you just want to get some tutorial projects up and running, WAMPserver (http://www.wampserver.com/en/) might be enough, but as soon as you bring frameworks or special Apache module requirements to the table, that will become more of a headache.

As for frameworks, I think Laravel is the current framework most recommended especially for beginners, although there are many very good alternatives and this is a very debatable topic. I'm not sure jumping straight into a framework is the best idea though, I would rather start here: http://www.phptherightway.com/ - this also has a short bit about Vagrant.

Vedder
Jun 20, 2006

Hello people just a quick question on arrays and php_self (probably very simple):

I have a database query which retrieves a list of items, at the same time I create an array containing the elements "Enabled" and "Disabled", I put the database items in an array and put the enabled/disabled at the end of each one, I then loop through and I end up with:

Item 1 - drop down list (enabled/disabled)
Item 2 - drown down list (enabled/disabled)
....
....
Submit button

The above it exactly what I planned, the idea is users get the initial data, all set to "Enabled" and they can choose to "disable" items. What I want to happen next is they click submit and the array is passed to another function where i can remove the elements according to whether the user chose to disable them.

I have a simple form which goes to the same page using php_self, however I am completely unable to get the array to this section, I can get variables there no problem, just nothing with the array, no error messages and the rest of the page loads as normal. I have tried testing this with session variables, hidden inputs and I had a quick look at serialising. To be absolutely basic I even tried a print_r and it displays nothing after being submitted.

code:
if(isset($_POST['submit'])) 
{ 
print_r($combinedArray);	
}
I think have a simple form declaration
code:
<form action=<?php echo $_SERVER['PHP_SELF'];?> method="post">


I can pass the array to other functions on the page, manipulate values but as soon as I submit the page acts like it has never heard of it. Anyone had this before or can see where I am going wrong?

Mister Chief
Jun 6, 2011

Can you post the entire page?

Jabor
Jul 16, 2010

#1 Loser at SpaceChem
Submitting the form essentially reloads the page, so the user hits a new instance of your PHP code that doesn't have the foggiest idea about what variables got set last time.

If you want to store data so it can be accessed after the user reloads the page, use session variables. If you want to see what values the user set on the form, check $_POST.

crabrock
Aug 2, 2002

I

AM

MAGNIFICENT






$normalvariables don't persist to page reloads (which is what post does).

You need to do something like <input type="checkbox" value="1" name="option1">

and do something like this on the page reload:

for ($_POST as $key => $value) { if ($value) { echo "<input type=\"checkbox\" value=\"1\" name=\"option1\">"; } }

Vedder
Jun 20, 2006

crabrock posted:

$normalvariables don't persist to page reloads (which is what post does).

You need to do something like <input type="checkbox" value="1" name="option1">

and do something like this on the page reload:

for ($_POST as $key => $value) { if ($value) { echo "<input type=\"checkbox\" value=\"1\" name=\"option1\">"; } }

That was exactly what I needed, thanks for your replies, I had a problem where the while loop was going through, assigning the variables but then the session variable would only display the last element in the array.

Time to do a bit more reading on arrays and I should be ok.

jony neuemonic
Nov 13, 2009

What's the preferred way to set your Laravel app's key automatically without having it in version control? In Rails I usually do this, based on RailsTutorial, and then add .secret to .gitignore to keep it private:

Ruby code:
def secure_token
  token_file = Rails.root.join('.secret')
  if File.exist?(token_file)
    # Use the existing token.
    File.read(token_file).chomp
  else
    # Generate a new token and store it in token_file.
    token = SecureRandom.hex(64)
    File.write(token_file, token)
    token
  end
end
MyApp::Application.config.secret_key_base = secure_token
Is there a more idiomatic way for Laravel? If not, what's my best bet for duplicating this in PHP? openssl_random_pseudo_bytes?

IcedPee
Jan 11, 2008

Yarrrr! I be here to plunder the fun outta me workplace! Avast!

FREE DECAHEDRON!
I'm completely new to PHP and JSON.

I need to serialize some info from my database into JSON in a format given here:
code:
{
    "timeline":
    {
        "headline":"The Main Timeline Headline Goes here",
        "type":"default",
        "text":"<p>Intro body text goes here, some HTML is ok</p>",
        "asset": {
            "media":"http://yourdomain_or_socialmedialink_goes_here.jpg",
            "credit":"Credit Name Goes Here",
            "caption":"Caption text goes here"
        },
        "date": [
            {
                "startDate":"2011,12,10",
                "endDate":"2011,12,11",
                "headline":"Headline Goes Here",
                "text":"<p>Body text goes here, some HTML is OK</p>",
                "tag":"This is Optional",
                "classname":"optionaluniqueclassnamecanbeaddedhere",
                "asset": {
                    "media":"http://twitter.com/ArjunaSoriano/status/164181156147900416",
                    "thumbnail":"optional-32x32px.jpg",
                    "credit":"Credit Name Goes Here",
                    "caption":"Caption text goes here"
                }
            }
        ],
        "era": [
            {
                "startDate":"2011,12,10",
                "endDate":"2011,12,11",
                "headline":"Headline Goes Here",
                "text":"<p>Body text goes here, some HTML is OK</p>",
                "tag":"This is Optional"
            }

        ]
    }
}
While I have no problems pulling data out, I can't seem to get the JSON part right. Here's what I have:

code:
<?php
 
// ensure connection using our local config 
require_once('config.php');
$conn = mysql_connect(DB_HOST, DB_USER, DB_PASSWORD);

if (!$conn ) 
{
   die('Not connected : ' . mysql_error());
}

// select db
$dbconn = mysql_select_db(DB_DATABASE,$conn);
if (!$dbconn ) 
{
   die ('Can\'t select db : ' . mysql_error());
}



// generating event attributes inside a function
function eventAtt() 
{
   $eventQuery=mysql_query('SELECT * FROM timelineevents')  or die (mysql_error());
   while ($row = mysql_fetch_array($eventQuery)) 
   {
       $date = explode("-", $row['Time']); // $date is stored as mm-dd-yyyy-hh
       $phpmakedate = mktime($date[3], 0, 0, $date[0], $date[1], $date[2]);
	   
	   
       // create array
       $eventAtts[] = array 
       (
               'startDate' => date("r",$phpmakedate),
               'endDate' => $phpmakedate,
               'headline' => 'I am a headline!',
               'text' => $row['User']
       );
   }

   mysql_free_result($eventQuery);
   return $eventAtts;
}


$json_data = array 
(
        //Timeline attributes
        'type'=>'default',
        'headline'=>'I am a main headline',

        //Event attributes
        'date'=> eventAtt(),
        'era' => array
            (
                "startDate"=>"2011,12,10",
                "endDate"=>"2011,12,11",
                "headline"=>"Headline Goes Here",
                "text"=>"<p>Body text goes here, some HTML is OK</p>",
                "tag"=>"This is Optional"
            )
);

$json_encoded=json_encode($json_data);
echo $json_encoded;

?>
Am I on the right track? I've looked at some tutorials, but yet to find a tutorial on how to create a JSON object based on a given model. They all say "JSON is very picky" but then all create the object very differently.

Any guidance helps.

Edit: forgot my 'era' attribute

IcedPee fucked around with this message at 19:10 on Nov 25, 2013

musclecoder
Oct 23, 2006

I'm all about meeting girls. I'm all about meeting guys.
What isn't right about it? If you're missing the main 'timeline' key, add one more level to your array:

php:
<?php

// ... code ...

$json_data = array(
    'timeline' => array(
        'type' => 'default',
        'headline' => 'I am a main headline',
        'asset' => array(
            'media' => 'media',
            'credit' => 'credit',
            'caption' => 'caption'
        ),
        'date' => eventAtt(),
        'era' => array(
            'startDate' => '2011,12,10',
            'endDate' => '2011,12,11',
            'headline' => 'Headline Goes Here',
            'text' => '<p>Body text goes here, some HTML is OK</p>',
            'tag' => 'This is Optional'
        )
    )
);

Shy
Mar 20, 2010

e: actually, nevermind

Shy fucked around with this message at 19:42 on Nov 25, 2013

IcedPee
Jan 11, 2008

Yarrrr! I be here to plunder the fun outta me workplace! Avast!

FREE DECAHEDRON!
Blah. I was just missing that timeline key.

jony neuemonic
Nov 13, 2009

IcedPee posted:

I'm completely new to PHP and JSON.

I need to serialize some info from my database into JSON in a format given here:

php:
<?
// code...
?>

Glad to see you got this working. Just FYI though, you should really be using either PDO or MySQLi. The original MySQL extension is deprecated, on top of being a huge pain to work with.

http://www.php.net/manual/en/mysqlinfo.api.choosing.php

I prefer PDO, but either one is going to make your life a lot easier.

IcedPee
Jan 11, 2008

Yarrrr! I be here to plunder the fun outta me workplace! Avast!

FREE DECAHEDRON!
I actually don't really need to do anything complex with SQL other than CRUD ops, but thanks for the heads up on the deprecated API.

fletcher
Jun 27, 2003

ken park is my favorite movie

Cybernetic Crumb

IcedPee posted:

I actually don't really need to do anything complex with SQL other than CRUD ops, but thanks for the heads up on the deprecated API.

Even if that's the case you should still use PDO.

Vintersorg
Mar 3, 2004

President of
the Brendan Fraser
Fan Club



Any recommendations for PDF generation? One of the guys here used to use FPDF but I am reading about TCPDF being a better alternative.

These will basically be certificates they print out plus they think maybe table markers and name tags. So it'll take information from a form and pop it into a PDF document.

Vintersorg fucked around with this message at 17:35 on Nov 26, 2013

DaTroof
Nov 16, 2000

CC LIMERICK CONTEST GRAND CHAMPION
There once was a poster named Troof
Who was getting quite long in the toof

Vintersorg posted:

Any recommendations for PDF generation? One of the guys here used to use FPDF but I am reading about TCPDF being a better alternative.

These will basically be certificates they print out plus they think maybe table markers and name tags. So it'll take information from a form and pop it into a PDF document.

I've had good luck generating PDFs from HTML with dompdf.

musclecoder
Oct 23, 2006

I'm all about meeting girls. I'm all about meeting guys.
I second DOMPDF, it's great. And if you use Symfony, use this bundle which is a nice wrapper for it: https://packagist.org/packages/slik/dompdf-bundle

revmoo
May 25, 2006

#basta
DomPDF is killer. Another team did some pdf work using tcpdf marking out coordinates, and it took forever. I did a similar project and used DomPDF and it took like 30 mins..

I seem to remember it not supporting css box model stuff but it's still a lifesaver.

McGlockenshire
Dec 16, 2005

GOLLOCKS!
Don't disregard wkhtmltopdf. It's a touch out of date now, but it still works beautifully.

Vintersorg
Mar 3, 2004

President of
the Brendan Fraser
Fan Club



Thanks guys! That DOMpdf is greatness - nice and easy to use.

Cthulhuite
Mar 22, 2007

Shwmae!
I'm not the best at PHP coding, but i'm learning a bit more every day and this project has helped!

I'm building a database for a set of Pen & Paper games a bunch of friends play. I'd like a very rudimentary events calendar, that basically pulls the event time and day out of the database table, then adjusts it for timezone difference before displaying it.

The day is stored in column game_day, time is stored in game_time as UTC (I can change the format), and the timezone is set at user registration and kept in a session. It usues the PHP timezone format, so it's stored as 'Americas\Halifax' or whatever.

What's the easiest way to go about doing this? Everything i've looked up online is for adjusting the current time/day, which won't help me right now. Any help would be appreciated, or any directions on where/what to look into for figuring it out myself.

Pseudo-God
Mar 13, 2006

I just love oranges!
Is there any library that will allow me to place a texture on an image, but allow me to 3D transform it beforehand? I am having difficulty finding the terms to describe this in google, but I want to take this image:

Apply this texture:

And achieve this result:


I will define the surfaces of the image beforehand, so the library does not have to guess where to place the thing. There will not be a 3D model of the object. Something similar to what I want is here:
http://configurator.audi.co.uk/entry?.html=&context=accx-uk%3Agb-en
But I also want to be able to upload my own textures.

Any tips on where I might find something like this?

The Laplace Demon
Jul 23, 2009

"Oh dear! Oh dear! Heisenberg is a douche!"
Imagick::distortImage and Imagick::compositeImage should do it. You're going to have to play around with the control points and offsets for rendering onto the cube, but it's basically like this:

php:
<?php
$cube = new Imagick('cube.png');
$face1 = new Imagick('face.png');
$face2 = clone $face1;
$face3 = clone $face2;

$height $face1->getImageHeight();
$width $face1->getImageWidth();
$face1ControlPoints = array(00// top left x,y before
                            00// top left x,y after

                            0$height// bottom left
                            0100,

                            $width$height// bottom right
                            100100,

                            $width0// top right
                            1000,
                            );

// distort to make perfect 100x100 square
$face1->distortImage(Imagick::DISTORTION_PERSPECTIVE$face1ControlPointstrue);
// do the same for $face2 and $face3

// these are the coordinates $face1 will be offset in the cube image
$x1 0;
$y1 0;
$cube->compositeImage($face1Imagick::COMPOSITE_ATOP$x1$y1);
// do the same for $face2 and $face3

$cube->writeImage('new-cube.png');
?>

The Laplace Demon fucked around with this message at 21:48 on Dec 2, 2013

McGlockenshire
Dec 16, 2005

GOLLOCKS!

Cthulhuite posted:

I'd like a very rudimentary events calendar, that basically pulls the event time and day out of the database table, then adjusts it for timezone difference before displaying it.

The day is stored in column game_day, time is stored in game_time as UTC (I can change the format), and the timezone is set at user registration and kept in a session. It usues the PHP timezone format, so it's stored as 'Americas\Halifax' or whatever.

What's the easiest way to go about doing this? Everything i've looked up online is for adjusting the current time/day, which won't help me right now.

You're already doing the right thing by storing the datetime as UTC. The easiest way to deal with this is going to be using DateTime and DateTimeZone:

php:
<?
$display_zone = new DateTimeZone('America/Los_Angeles');
$timestamp = 1386016456;

$original_datetime = new DateTime('@' . $timestamp);
$adjusted_datetime = clone $original_datetime;
$adjusted_datetime->setTimezone($display_zone);

echo "Original: ", $original_datetime->format('Y-m-d H:i:s e'); // Original: 2013-12-02 20:34:16 +00:00
echo "\nAdjusted: ", $adjusted_datetime->format('Y-m-d H:i:s e'); // Adjusted: 2013-12-02 12:34:16 America/Los_Angeles
?>
Giving the @ syntax to the DateTime constructor tells it that it's a Unix timestamp and to set the timezone to UTC. If you are using something other than a Unix timestamp, then you'll need to create a UTC DateTimeZone instead:

php:
<?
$utc_zone = new DateTimeZone('UTC');
$display_zone = new DateTimeZone('America/Los_Angeles');
$timestamp = '2013-12-02 12:42:13';

$original_datetime = new DateTime($timestamp, $utc_zone);
$adjusted_datetime = clone $original_datetime;
$adjusted_datetime->setTimezone($display_zone);

echo "Original: ", $original_datetime->format('Y-m-d H:i:s e'); // Original: 2013-12-02 12:42:13 UTC
echo "\nAdjusted: ", $adjusted_datetime->format('Y-m-d H:i:s e'); // Adjusted: 2013-12-02 04:42:13 America/Los_Angeles
?>
Note the different treatment the UTC timezone gets when it's expressly told that it's UTC versus the implicit UTC of the Unix timestamp.

Also note that I'm cloning the datetime here. They're mutable, so you have to be careful sometimes...

McGlockenshire fucked around with this message at 21:46 on Dec 2, 2013

Pseudo-God
Mar 13, 2006

I just love oranges!
Man, this is exactly what I was looking for. I will show you guys the awesome results a bit later. Thanks for this!

Cthulhuite
Mar 22, 2007

Shwmae!

McGlockenshire posted:

You're already doing the right thing by storing the datetime as UTC. The easiest way to deal with this is going to be using DateTime and DateTimeZone:

php:
<?
$display_zone = new DateTimeZone('America/Los_Angeles');
$timestamp = 1386016456;

$original_datetime = new DateTime('@' . $timestamp);
$adjusted_datetime = clone $original_datetime;
$adjusted_datetime->setTimezone($display_zone);

echo "Original: ", $original_datetime->format('Y-m-d H:i:s e'); // Original: 2013-12-02 20:34:16 +00:00
echo "\nAdjusted: ", $adjusted_datetime->format('Y-m-d H:i:s e'); // Adjusted: 2013-12-02 12:34:16 America/Los_Angeles
?>
Giving the @ syntax to the DateTime constructor tells it that it's a Unix timestamp and to set the timezone to UTC. If you are using something other than a Unix timestamp, then you'll need to create a UTC DateTimeZone instead:

php:
<?
$utc_zone = new DateTimeZone('UTC');
$display_zone = new DateTimeZone('America/Los_Angeles');
$timestamp = '2013-12-02 12:42:13';

$original_datetime = new DateTime($timestamp, $utc_zone);
$adjusted_datetime = clone $original_datetime;
$adjusted_datetime->setTimezone($display_zone);

echo "Original: ", $original_datetime->format('Y-m-d H:i:s e'); // Original: 2013-12-02 12:42:13 UTC
echo "\nAdjusted: ", $adjusted_datetime->format('Y-m-d H:i:s e'); // Adjusted: 2013-12-02 04:42:13 America/Los_Angeles
?>
Note the different treatment the UTC timezone gets when it's expressly told that it's UTC versus the implicit UTC of the Unix timestamp.

Also note that I'm cloning the datetime here. They're mutable, so you have to be careful sometimes...

This is absolutely amazing, thank you! It only took me about 5 minutes to slot it into my current code and have it working, you're an absolute diamond!

IT BEGINS
Jan 15, 2009

I don't know how to make analogies
I'm creating a data upload script that accepts big pieces of tab-separated data copied directly from excel. I am trying to make sure I am filtering this data so that it can be inserted into the database securely. However, since I only have a $_POST['data'] variable coming in, I am not sure exactly how I should filter it.

Normally, I split this data by the line endings, split each resulting line by tabs, then combine it with an existing array of fields before inserting through a prepared statement. What follows is a simplified example:

php:
<?
$fields = array('id', 'name', 'date');
$data = $_POST['data'];
$lines = explode("\n", $data);

foreach ($lines as $line) {
    $row = explode("\t", $data);
    $pdo->insert('mytable', array_combine($fields, $row));
}
?>
Should I be sanitizing each individual field with filter_var after I've split each line up? Are there any specific filters I should use, or just whatever I actually expect to be storing?

McGlockenshire
Dec 16, 2005

GOLLOCKS!

Vasja posted:

Should I be sanitizing each individual field with filter_var after I've split each line up?

Maybe. Can we also see your custom insert method? Depending on what it does, you might be perfectly safe here.

Alternatively, consider letting users just upload the Excel file, or a CSV export of it. This eliminates a big window of users causing problems. I've heard that PHPExcel doesn't suck too horribly.

IT BEGINS
Jan 15, 2009

I don't know how to make analogies
My insert method is as follows:

php:
<?
class PDOAdapter
{
    public function insert($table, array $params)
    {
        $cols = implode(", ", array_keys($params));
        $placeholders = substr(str_repeat("?,", count($params)), 0, -1);
        $sql = "INSERT INTO $table ($cols) VALUES ($placeholders)";
        return $this->query($sql, $params);
    }

    public function query($sql, $params)
    {
        $statement = $this->pdo->prepare($sql);
        $statement->execute(array_values($params));
        return $statement;
    }
}
?>
Wouldn't I still need to do sanitation for excel files or csv? If they insert bogus data or javascript into fields that shouldn't have them, I'd still need to handle that, right?

McGlockenshire
Dec 16, 2005

GOLLOCKS!

Vasja posted:

My insert method is as follows:

Standard operating procedure. You're doing everything correctly there. Almost. You should be extending PDO instead of wrapping it, but whatever.

quote:

Wouldn't I still need to do sanitation for excel files or csv? If they insert bogus data or javascript into fields that shouldn't have them, I'd still need to handle that, right?

It all depends on what the data actually is. If the name field should only contain alphanumerics and punctuation, validate that. If the date field is actually being stored as a date in the database, you should run it through strtotime() or make it a DateTime to validate it and then format it correctly.

If these are internal users, then you might not need to go all-out on the validation front. If you're worried about displaying bogus data, consider doing a call to htmlspecialchars when displaying the name, as that'll kill any HTML that might have come in.

Weird Uncle Dave
Sep 2, 2003

I could do this all day.

Buglord
I'm temporarily stumped by something that works, but also doesn't work.

code:
<?php shell_exec('/usr/bin/git pull ssh://my-git-server/git/my-wordpress-theme /home/user/wp-content/themes/my-wordpress-theme'); ?>
(It's eventually going to be part of a WordPress plugin, but since I'm not using any WordPress-specific stuff at this time it shouldn't matter.)

The above works if the Git repo is an http:// or https:// URL. Unfortunately, the repo I need to pull from is only available via SSH.

I created an SSH key pair, and when I'm logged into the server as the user and run the script ('php-cli myscript.php'), the script works as expected. But it doesn't work when you run the code as a Web page (by entering its URL into a browser, or with wget). I get an SSH login error; it looks like the script can no longer see the SSH key files.

Either way, the script is running as the same user (I use mod_suphp to ensure this).

Aside from a few environment variables, I can't think of any differences in how the script would execute locally versus remotely. What am I overlooking?

Sulla Faex
May 14, 2010

No man ever did me so much good, or enemy so much harm, but I repaid him with ENDLESS SHITPOSTING
How can I get REMOTE_USER info without requiring the user to log in using mod_auth_sspi? I've been googling like crazy but I'm stuck on a hurdle which is just a basic understanding of how the web server gets the user domain login info automagically, without requiring a manual login. I've found a thousand different solutions that don't really explain it and just assume that you've already got REMOTE_USER somehow.

It's in an AD environment using IE to grab the user's domain login details. Running PHP on Apache on Windows Server 2008. I've been told http headers but getallheaders() doesn't output what I'm looking for. Should I be looking somewhere else or does the fault lie with group policy settings that aren't broadcasting the login name through http headers to trusted sites (i.e. mine)?

I will be authenticating through another (non-PHP/apache) service but I need the username without popping up a login window.

spacebard
Jan 1, 2007

Football~

Sulla-Marius 88 posted:

It's in an AD environment using IE to grab the user's domain login details. Running PHP on Apache on Windows Server 2008. I've been told http headers but getallheaders() doesn't output what I'm looking for. Should I be looking somewhere else or does the fault lie with group policy settings that aren't broadcasting the login name through http headers to trusted sites (i.e. mine)?

Is the header in the http request at all? You may be able to view the raw request in IE developer tool these days. It's possible with Firefox, Chrome, etc...

If there is supposed to be a http header set, then I'd verify it's absinthe sent. Maybe apache access log can reveal it if configured? Man, I hate debugging in IE...

Wheany
Mar 17, 2006

Spinyahahahahahahahahahahahaha!

Doctor Rope
Is the PHP 5.5 password_hash function compatible with phpass, assuming bcrypt?

I think bcrypt uses a standard format, but I don't want it biting me in the rear end.

Sulla Faex
May 14, 2010

No man ever did me so much good, or enemy so much harm, but I repaid him with ENDLESS SHITPOSTING

Sulla-Marius 88 posted:

How can I get REMOTE_USER info without requiring the user to log in using mod_auth_sspi? I've been googling like crazy but I'm stuck on a hurdle which is just a basic understanding of how the web server gets the user domain login info automagically, without requiring a manual login. I've found a thousand different solutions that don't really explain it and just assume that you've already got REMOTE_USER somehow.

It's in an AD environment using IE to grab the user's domain login details. Running PHP on Apache on Windows Server 2008. I've been told http headers but getallheaders() doesn't output what I'm looking for. Should I be looking somewhere else or does the fault lie with group policy settings that aren't broadcasting the login name through http headers to trusted sites (i.e. mine)?

I will be authenticating through another (non-PHP/apache) service but I need the username without popping up a login window.

spacebard posted:

Is the header in the http request at all? You may be able to view the raw request in IE developer tool these days. It's possible with Firefox, Chrome, etc...

If there is supposed to be a http header set, then I'd verify it's absinthe sent. Maybe apache access log can reveal it if configured? Man, I hate debugging in IE...

These are the steps I took to get it working. I'm about to fully configure NTLM to login but this puts the username in the $_SERVER vars for me. It will differ based on your php set up.

Include mod_auth_sspi.so in your mods folder.

Check that apache httpd.conf includes the relevant mods (headers, auth_sspi, basic auth etc).

The basic premise is:

Designate a folder or file to be your 'authentication' page.
Set mod_auth_sspi to function in that page/location and rewrite headers so that the username is passed into the headers where PHP can get it.
Everywhere else on your site, you check if user is logged in through your site's session system -- if not, redirect them to a page within the "authentication" folder, which gets the user details via SSPI, authenticates through NTLM, and then automatically logs the user in to your site's authentication system (i.e. creating a valid session), and redirect the user back to the previous page.

This is what I chucked in my httpd.conf file. $_SERVER['USER_NAME'] should return the domain and username (e.g. "DOMAIN\useraccount"), although if you var_dump($_SERVER) you'll notice that it's being sent in other forms anyway via SSPI, like REMOTE_USER.

code:
	<Location  "/login/ntlm" >
		AuthName "ClientName NTLM"
		AuthType SSPI
		SSPIAuth On
		SSPIAuthoritative On
		SSPIOfferBasic On      # let non-IE clients authenticate
		SSPIBasicPreferred Off # should basic authentication have higher priority?
		require valid-user
		RewriteEngine On
		RewriteRule ^(.*)$ - [E=USER_NAME:%{REMOTE_USER}]  
         </Location>
This is probably really rudimentary and a lovely explanation but I'll leave it here in case other people are searching for what I was yesterday.

Sulla Faex fucked around with this message at 10:59 on Dec 12, 2013

Weird Uncle Dave
Sep 2, 2003

I could do this all day.

Buglord

Weird Uncle Dave posted:

code:
<?php shell_exec('/usr/bin/git pull ssh://my-git-server/git/my-wordpress-theme /home/user/wp-content/themes/my-wordpress-theme'); ?>

Following up on my problem: I knew it wasn't a PHP issue, but it was actually an SELinux issue. I'd have to add this to a SELinux policy somewhere:
code:
allow httpd_t ssh_home_t:file read;
And there are just too many things that could go wrong, security-wise, for me to think that's even remotely a good idea.

Adbot
ADBOT LOVES YOU

McGlockenshire
Dec 16, 2005

GOLLOCKS!

Wheany posted:

Is the PHP 5.5 password_hash function compatible with phpass, assuming bcrypt?

I think bcrypt uses a standard format, but I don't want it biting me in the rear end.

Assuming bcrypt and portable mode is turned off, then yes, phpass produces the same bcrypt hash as a crypt() call. Kind of. It produces "2a" hashes, which while they can be read and verified by password_verify(), they are potentially subject to being complained about due to previous bcrypt bugs in PHP. If your PHP generates "2y" hashes by default, then you're fine.

If you're using 5.3 you should be using password_compat instead of phpass.

  • 1
  • 2
  • 3
  • 4
  • 5
  • Post
  • Reply