php-general Digest 1 Jan 2010 23:38:40 -0000 Issue 6517

Topics (messages 300771 through 300776):

Re: If design patterns are not supposed to produce reusable code then why use 
them?
        300771 by: Tony Marston
        300772 by: Larry Garfield

Re: PHP uploaded files logs
        300773 by: Kim Madsen
        300774 by: Ashley Sheridan
        300775 by: Daniel Egeberg

Arrays & Regexp - Help Requested
        300776 by: Allen McCabe

Administrivia:

To subscribe to the digest, e-mail:
        php-general-digest-subscr...@lists.php.net

To unsubscribe from the digest, e-mail:
        php-general-digest-unsubscr...@lists.php.net

To post to the list, e-mail:
        php-gene...@lists.php.net


----------------------------------------------------------------------
--- Begin Message ---
"Larry Garfield" <la...@garfieldtech.com> wrote in message 
news:200912311743.16759.la...@garfieldtech.com...
> Meant to send this to the list, sorry.
>
> ----------  Forwarded Message  ----------
>
> Subject: Re: [PHP] If design patterns are not supposed to produce reusable
> code then why use them?
> Date: Thursday 31 December 2009
> From: Larry Garfield <la...@garfieldtech.com>
> To: "Tony Marston" <t...@marston-home.demon.co.uk>
>
> On Wednesday 30 December 2009 10:50:40 am Tony Marston wrote:
>> I have recently been engaged in an argument via email with someone who
>> criticises my low opinion of design patterns (refer to
>> http://www.tonymarston.net/php-mysql/design-patterns.html ). He says that
>> design patterns are merely a convention and not a reusable component. My
>> argument is that something called a pattern is supposed to have a 
>> recurring
>> theme, some element of reusability, so that all subsequent 
>> implementations
>> of a pattern should require less effort than the first implementation. If
>> design patterns do not provide any reusable code then what is the point 
>> of
>> using them?
>>
>>
>>
>> I do not use design patterns as I consider them to be the wrong level of
>> abstraction. I am in the business of designing and developing entire
>> applications which comprise of numerous application transactions, so I 
>> much
>> prefer to use transaction patterns (refer to
>> http://www.tonymarston.net/php-mysql/design-patterns-are-dead.html and
>> http://www.tonymarston.net/php-mysql/transaction-patterns.html ) as these
>> provide large amounts of reusable code and are therefore a significant 
>> aid
>> to programmer productivity.
>>
>>
>>
>> What is your opinion? Are design patterns supposed to provide reusable 
>> code
>> or not? If not, and each implementation of a pattern takes just as much
>>  time as the first, then where are the productivity gains from using 
>> design
>>  patterns?
>
> It depends what you're reusing.  Design patterns are reusable concepts, 
> not
> reusable code.  That's the key difference.
>
> Knowledge of design patterns is like knowledge of how different food
> ingredients interact.  "Hm, this needs something to bring out the taste 
> more,
> so I'll add salt."  You're not going to add the same salt to each dish,
> obviously, but the idea is that you need something that will bring out the
> taste, and there are certain spices that will bring out the existing taste 
> of
> whatever it is you put them on, such as salt.

Food recipes are a bad analogy for design patterns. A food recipe explicitly 
identifies a list of ingredients and a list of actions which are required to 
produce the intended result. The design pattern equivalent of a recipe would 
simply state "take a bunch of ingredients, mix them up, heat them up, serve 
them up". A design pattern merely identifies the concept, not the 
implementation, so where is the REAL benefit? Where is the re-usability?

> Similarly, if you want, say, a piece of code that will connect to a 
> database,
> you want a pre-built library, not a design pattern.  (There's no shortage 
> of
> those.)  If, however, you want a mechanism by which you can have different
> implementations of the same system, and want to swap them out without
> rewriting the calling code, then what you want is the factory *pattern*.
> There may not be existing code yet for whatever system you're writing.
> However, once you recognize "Ah, I want a common interface with a 
> swappable
> implementation, and I want to pick the implementation at runtime based on 
> some
> arbitrarily complex logic", then you know you don't need to think through 
> how
> you go about structuring the code to do that.  Instead, you look up a
> description of the factory pattern and go "ah, that makes sense, and it 
> solves
> 3 problems that I didn't realize I'd run into later".  Then you go and
> implement code that follows that pattern, and you don't have to think 
> through
> the algorithm.

I would not use the factory pattern for such a thing. I have actually 
written an application which can switch between database engines - MySQL, 
PostgreSQL and Oracle - simply by changing a single line of code. Although I 
*could* use the factory pattern, in my experience it would be overkill and 
too complicated.


> Now, it is possible to make generic implementations of some patterns that 
> you
> can re-leverage.  Eg, you can have a common factory interface and a way to
> request a factory, which in turn will give you the implementation object 
> you
> want.  The common elements of those factories you move up to a parent 
> class,
> and therefore reuse code that way.  This is known as a "Factory factory", 
> and
> is in some cases very useful and in others gross over-engineering. 
> Knowing
> which is which is something you learn through experience.

The very idea of a "factory factory" fills me with nausea. I have seen 
several examples and my immediate response has always been "real programmers 
don't write code like that". Yet too many programmers are taught that they 
MUST use design patterns, so they follow blindly without any regard for the 
consequences.

Tony Marston



--- End Message ---
--- Begin Message ---
On Friday 01 January 2010 05:26:48 am Tony Marston wrote:

> > It depends what you're reusing.  Design patterns are reusable concepts,
> > not
> > reusable code.  That's the key difference.
> >
> > Knowledge of design patterns is like knowledge of how different food
> > ingredients interact.  "Hm, this needs something to bring out the taste
> > more,
> > so I'll add salt."  You're not going to add the same salt to each dish,
> > obviously, but the idea is that you need something that will bring out
> > the taste, and there are certain spices that will bring out the existing
> > taste of
> > whatever it is you put them on, such as salt.
> 
> Food recipes are a bad analogy for design patterns. A food recipe
>  explicitly identifies a list of ingredients and a list of actions which
>  are required to produce the intended result. The design pattern equivalent
>  of a recipe would simply state "take a bunch of ingredients, mix them up,
>  heat them up, serve them up". A design pattern merely identifies the
>  concept, not the
> implementation, so where is the REAL benefit? Where is the re-usability?

Note that I did not say that design patterns are a recipe.  I said they're 
knowledge of how different foods interact.  They're meta-knowledge that makes 
you a better chef, not a faster short-order cook.

> > Similarly, if you want, say, a piece of code that will connect to a
> > database,
> > you want a pre-built library, not a design pattern.  (There's no shortage
> > of
> > those.)  If, however, you want a mechanism by which you can have
> > different implementations of the same system, and want to swap them out
> > without rewriting the calling code, then what you want is the factory
> > *pattern*. There may not be existing code yet for whatever system you're
> > writing. However, once you recognize "Ah, I want a common interface with
> > a swappable
> > implementation, and I want to pick the implementation at runtime based on
> > some
> > arbitrarily complex logic", then you know you don't need to think through
> > how
> > you go about structuring the code to do that.  Instead, you look up a
> > description of the factory pattern and go "ah, that makes sense, and it
> > solves
> > 3 problems that I didn't realize I'd run into later".  Then you go and
> > implement code that follows that pattern, and you don't have to think
> > through
> > the algorithm.
> 
> I would not use the factory pattern for such a thing. I have actually
> written an application which can switch between database engines - MySQL,
> PostgreSQL and Oracle - simply by changing a single line of code. Although
>  I *could* use the factory pattern, in my experience it would be overkill
>  and too complicated.

Oh really?  I've written such a DB abstraction system as well.  (I think most 
people have at some point.)  Although I did not specifically go into it saying 
"I will use a factory for this", in practice it really is.  Some client code 
says "hey, I need a DB connection, gimme!", an intermediary piece of code 
figures out which DB connection you need (based on configuration data, what 
servers are available, or whatever), and passes back a PDO connection object 
on which you run queries.  That's a factory, in a nutshell.  I suspect your DB 
abstraction system works on the same general principle.

Yes, you're already using common design patterns, I wager, even if you had to 
"invent" them yourself.

However, by understanding it AS a factory pattern, you can explain how it 
works to someone else through a common vocabulary.  You can also look at your 
implementation and see where it's going to be extensible and where it's not by 
comparing it to similar approaches that have already been tried and vetted.

The savings is in going "oh, hey, this approach to my problem has already been 
tried, and what I was going to do would have broken here, here, and here.  But 
by following this similar approach, I can avoid those problems and spend less 
time rewriting code later".

Yes, I have in fact run into that situation myself on more than one occasion.

> The very idea of a "factory factory" fills me with nausea. I have seen
> several examples and my immediate response has always been "real
>  programmers don't write code like that". Yet too many programmers are
>  taught that they MUST use design patterns, so they follow blindly without
>  any regard for the consequences.
> 
> Tony Marston

"Real programmers" don't make jibes about what "real programmers" do out of 
ignorance.

Yes, always blindly following a given design pattern for the sake of following 
a design pattern is stupid.  Blindly ignoring established "solved problems" 
just for the sake of avoiding those pointless design patterns is just as 
stupid.

Remember, code is irrelevant.  You don't sell code.  You sell ideas and 
concepts, implemented in code.  By not having to re-invent the ideas and 
concepts every time, you can save a great deal of time and effort, and 
potentially a great deal of code that you don't need to rewrite later from 
going down a dead-end.

There's two kinds of developers: Those that understand how they're using 
design patterns and those that don't understand design patterns. :-)  But both 
are, in practice, using them, even if some are doing so badly (either over- or 
under-using them).

--Larry Garfield

--- End Message ---
--- Begin Message ---
Hi

Manoj Singh wrote on 01/01/2010 08:07:
Hi,

Is PHP maintaining the logs regarding files uploaded? Actually I needed it
because recently in my developed web site upload functionality seems to stop
working even for the correct file and i want to check that which type of
files are uploaded. Actually I cannot debug through PHP on the server as my
site is on production.

Not to my knowledge, but that should be pretty easy to create, just save all $_FILES['uploaded_file'] (or just $_FILES['uploaded_file']['tmp_name'], $_FILES['uploaded_file']['name'] and $_FILES['uploaded_file']['size']) into a logfile, note there's an error variable too.

--
Kind regards
Kim Emax - masterminds.dk

--- End Message ---
--- Begin Message ---
On Fri, 2010-01-01 at 14:10 +0100, Kim Madsen wrote:

> Hi
> 
> Manoj Singh wrote on 01/01/2010 08:07:
> > Hi,
> > 
> > Is PHP maintaining the logs regarding files uploaded? Actually I needed it
> > because recently in my developed web site upload functionality seems to stop
> > working even for the correct file and i want to check that which type of
> > files are uploaded. Actually I cannot debug through PHP on the server as my
> > site is on production.
> 
> Not to my knowledge, but that should be pretty easy to create, just save 
> all $_FILES['uploaded_file'] (or just 
> $_FILES['uploaded_file']['tmp_name'], $_FILES['uploaded_file']['name'] 
> and $_FILES['uploaded_file']['size']) into a logfile, note there's an 
> error variable too.
> 
> -- 
> Kind regards
> Kim Emax - masterminds.dk
> 


Wouldn't the Apache logs show this? Strictly speaking, the file upload
is handled by Apache first, which then passes details along to PHP to
deal with, so a problem might show there first.

Thanks,
Ash
http://www.ashleysheridan.co.uk



--- End Message ---
--- Begin Message ---
On Fri, Jan 1, 2010 at 14:28, Ashley Sheridan <a...@ashleysheridan.co.uk> wrote:
> Wouldn't the Apache logs show this? Strictly speaking, the file upload
> is handled by Apache first, which then passes details along to PHP to
> deal with, so a problem might show there first.

No, Apache doesn't log POST data only the request.

-- 
Daniel Egeberg

--- End Message ---
--- Begin Message ---
Happy New Year, here's my first question of the year (and it's only 15 hours
into the year!).

I am creating a small database management tool for my a website (my work IP
blocks my access to PhpMyAdmin) and I don't want to install any additional
software.

I am working on adding rows and need to format the input boxes properly (ie.
VARCHAR needs an text input, TEXT needs a textarea input). Using a mysql
query I can determine the data types for each field. I have a function that
uses this information to return datatype specific variables. For example
$field['field'] may equal int(6) or varchar(256).

The code is a bit extensive, but it's necessary to explain what's going on.

<?php
// Loop:
echo '<table width="100%" cellspacing="1" cellpadding="2" border="0">' .
"\n";
    foreach ($fields as $field)
    {
     // ROW BEGIN
     echo "\t" . '<tr>' . "\n";
     // NAME OF FIELD
     echo "\t\t" . '<td>`' . $field['field'] . '`: </td>' . "\n";
     // FIELD DATA TYPE
     echo "\t\t" . '<td>' . $field['type'] . '</td>' . "\n";
     // VALUE INPUT
     echo "\t\t" . '<td>';
     $input_type = printByType($field['type'], 'INPUT_TYPE');
     echo '<input type="' . $input_type . '" ';
     if ($input_type == 'text')
     {
      echo 'size="';
      $length = printByType($field['type'], 'INPUT_LENGTH');
      echo $length;
      echo '" ';
      echo 'value="';
      if ($field['null'] == 'YES') // CAN BE NULL?
      {
       echo 'NULL';
      }
      echo '" ';
     }
     elseif ($input_type == 'textarea')
     {
      echo 'rows="7" cols="30" ';
      echo 'value="';
      if ($field['null'] == 'YES') // CAN BE NULL?
      {
       echo 'NULL';
      }
      echo '" ';
     }
     echo 'name="value[]" id="value[]"
onfocus="if(this.value==\'NULL\')this.value=\'\';" />';
     echo '</td>' . "\n";
     echo "\t" . '</tr>' . "\n";
    }
    echo '</table>';

?>

The function:

<?php

function printByType($string, $mode)
 {
  (string) $string;
  $lengths = array(
    'VARCHAR' => 10
    , 'TINYINT' => 1
    , 'TEXT' => 10
    , 'DATE' => 7
    , 'SMALLINT' => 1
    , 'MEDIUMINT' => 2
    , 'INT' => 2
    , 'BIGINT' => 3
    , 'FLOAT' => 4
    , 'DOUBLE' => 4
    , 'DECIMAL' => 4
    , 'DATETIME' => 10
    , 'TIMESTAMP' => 10
    , 'TIME' => 7
    , 'YEAR' => 4
    , 'CHAR' => 7
    , 'TINYBLOB' => 10
    , 'TINYTEXT' => 10
    , 'BLOB' => 10
    , 'MEDIUMBLOB' => 10
    , 'MEDIUMTEXT' => 10
    , 'LONGBLOB' => 10
    , 'LONGTEXT' => 10
    , 'ENUM' => 5
    , 'SET' => 5
    , 'BIT' => 2
    , 'BOOL' => 1
    , 'BINARY' => 10
    , 'VARBINARY' => 10);
  $types = array(
    'VARCHAR' => 'text'
    , 'TINYINT' => 'text'
    , 'TEXT' => 'textarea'
    , 'DATE' => 'text'
    , 'SMALLINT' => 'text'
    , 'MEDIUMINT' => 'text'
    , 'INT' => 'text'
    , 'BIGINT' => 'text'
    , 'FLOAT' => 'text'
    , 'DOUBLE' => 'text'
    , 'DECIMAL' => 'text'
    , 'DATETIME' => 'text'
    , 'TIMESTAMP' => 'text'
    , 'TIME' => 'text'
    , 'YEAR' => 'text'
    , 'CHAR' => 'text'
    , 'TINYBLOB' => 'textarea'
    , 'TINYTEXT' => 'textarea'
    , 'BLOB' => 'textarea'
    , 'MEDIUMBLOB' => 'textarea'
    , 'MEDIUMTEXT' => 'textarea'
    , 'LONGBLOB' => 'textarea'
    , 'LONGTEXT' => 'textarea'
    , 'ENUM' => 'text'
    , 'SET' => 'text'
    , 'BIT' => 'text'
    , 'BOOL' => 'text'
    , 'BINARY' => 'text'
    , 'VARBINARY' => 'text');

  switch ($mode)
  {
   case 'INPUT_LENGTH':
    foreach ($lengths as $key => $val)
    {
     (string) $key;
     (int) $val;

     // DETERMINE LENGTH VALUE eg. int(6) GETS 6
     preg_match('#\((.*?)\)#', $string, $match);
     (int) $length_value = $match[1];

     // SEARCH
     $regex = "/" . strtolower($key) . "/i";
     $found = preg_match($regex, $string);

     if ($found !== false)
     {
      // DETERMINE ADD INTEGER eg. If the length_value is long enough,
determine number to increase html input length
      switch ($length_value)
      {
       case ($length_value <= 7):
        return $length_value;
       break;
       case ($length_value > 7 && $length_value < 15):
        return $val += ($length_value/2);
       break;
       case ($length_value > 14 && $length_value < 101):
        $result = ($length_value / 5);
        $divide = ceil($result);
        return $val += $divide;
       break;
       case ($length_value > 100):
        return 40;
       break;
       default:
        return 7;
       break;
      }
      return $val;
     }
     else
     {
      return 7; // default value
     }
    }
   break;

   case 'INPUT_TYPE':

    foreach ($types as $key => $val)
    {
     (string) $val;
     (string) $key;

     // SEARCH
     $regex = "/" . strtolower($key) . "/i";
     $found = preg_match($regex, $string);

     if ($found === false)
     {
      return 'text'; // default value
     }
     else
     {
      return $val;
     }
    }
   break;
  }

 }

?>

The first part of the function (the first switch case) works, and the text
fields are variable in length, but even the fields with a TEXT datatype is
printing out a text box instead of a textarea. Can anyone see why this is
happening?

Thanks!

--- End Message ---

Reply via email to