Commit 6327cf30 authored by Reinhold Kainhofer's avatar Reinhold Kainhofer
Browse files

Implement counter formatting/start/step directly in thee format

parent f8e9d77a
...@@ -4,13 +4,12 @@ OpenTools Advanced Ordernumbers for WooCommerce - Open TODOs ...@@ -4,13 +4,12 @@ OpenTools Advanced Ordernumbers for WooCommerce - Open TODOs
- Make sure the numbers are generated only for new orders, not for exsiting ones - Make sure the numbers are generated only for new orders, not for exsiting ones
- Check REST API - Check REST API
- Would it make sense to configure the order password format? - Would it make sense to configure the order password format?
- Implement custom variables
- Find out how multisite works and make the plugin work with it - Find out how multisite works and make the plugin work with it
- Add action to create an updated / new order number for an existing order - Add action to create an updated / new order number for an existing order
- implement woocommerce_hidden_order_itemmeta hook to hide the order number post meta? - implement woocommerce_hidden_order_itemmeta hook to hide the order number post meta?
- Use $order->order_date for the date-relating fields! - Use $order->order_date for the date-relating fields!
- Collect and return php warning messages (i.e. all other output) in the AJAX call and return it inside the JSON rather than as extra HTML. - Collect and return php warning messages (i.e. all other output) in the AJAX call and return it inside the JSON rather than as extra HTML.
- Create order number also when ordering in the frontend
HOOKS for order handling: HOOKS for order handling:
...@@ -37,4 +36,4 @@ woocommerce_new_order', $order_id ); ...@@ -37,4 +36,4 @@ woocommerce_new_order', $order_id );
Order created in BackEnd: Order created in BackEnd:
Created: wp_insert_post => Assign placeholder (no address yet) Created: wp_insert_post => Assign placeholder (no address yet)
Modified: Modified:
\ No newline at end of file
...@@ -85,11 +85,12 @@ if ( in_array( 'woocommerce/woocommerce.php', apply_filters( 'active_plugins', g ...@@ -85,11 +85,12 @@ if ( in_array( 'woocommerce/woocommerce.php', apply_filters( 'active_plugins', g
), ),
array( array(
'title' => self::__( 'Order number format'), 'title' => self::__( 'Order number format'),
'desc' => self::__( 'The format for the order numbers (variables can be entered as [...], the counter is indicated by the #). To use a different counter name than displayed, put the custom counter name after a |, e.g. "[year]-[month]/#|[year]" to use the month in the order number, but reset the counter only yearly.'), 'desc' => self::__( 'The format for the order numbers (variables can be entered as [...], the counter is indicated by the #). To use a different counter name than displayed, put the custom counter name after a |, e.g. "[year]-[month]/#|[year]" to use the month in the order number, but reset the counter only yearly. Advanced settings for the counter can be added as [#####:start/step], e.g. [#:100] to start new counters at 100, or [#/5] to increment the counter by 5. The number of # in the format determine how many digits are shown at least, e.g. [########] will always show at least 8 digits for the counter, e.g. 00000014.'),
'desc_tip' => true, 'desc_tip' => true,
'id' => 'ordernumber_format', 'id' => 'ordernumber_format',
'default' => '#', 'default' => '#',
'type' => 'text', 'type' => 'text',
'css' => 'width: 100%',
), ),
array( array(
'title' => self::__( 'Use global counter'), 'title' => self::__( 'Use global counter'),
...@@ -97,32 +98,32 @@ if ( in_array( 'woocommerce/woocommerce.php', apply_filters( 'active_plugins', g ...@@ -97,32 +98,32 @@ if ( in_array( 'woocommerce/woocommerce.php', apply_filters( 'active_plugins', g
'desc_tip' => true, 'desc_tip' => true,
'id' => 'ordernumber_global', 'id' => 'ordernumber_global',
'type' => 'checkbox', 'type' => 'checkbox',
'default' => 'no' 'default' => 'no',
),
array(
'title' => self::__( 'Counter Digits'),
'desc' => self::__( 'Minimum number of digits for the number'),
'desc_tip' => true,
'id' => 'ordernumber_padding',
'type' => 'number',
'default' => '0'
),
array(
'title' => self::__( 'Counter Start'),
'desc' => self::__( 'Start value for each new counter'),
'desc_tip' => true,
'id' => 'ordernumber_start',
'type' => 'number',
'default' => '1'
),
array(
'title' => self::__( 'Counter step'),
'desc' => self::__( 'By how much the counter will be increased after each order. Typically 1.'),
'desc_tip' => true,
'id' => 'ordernumber_step',
'type' => 'number',
'default' => '1'
), ),
// array(
// 'title' => self::__( 'Counter Digits'),
// 'desc' => self::__( 'Minimum number of digits for the number'),
// 'desc_tip' => true,
// 'id' => 'ordernumber_padding',
// 'type' => 'number',
// 'default' => '0'
// ),
// array(
// 'title' => self::__( 'Counter Start'),
// 'desc' => self::__( 'Start value for each new counter'),
// 'desc_tip' => true,
// 'id' => 'ordernumber_start',
// 'type' => 'number',
// 'default' => '1'
// ),
// array(
// 'title' => self::__( 'Counter step'),
// 'desc' => self::__( 'By how much the counter will be increased after each order. Typically 1.'),
// 'desc_tip' => true,
// 'id' => 'ordernumber_step',
// 'type' => 'number',
// 'default' => '1'
// ),
array( 'type' => 'sectionend', 'id' => 'ordernumber_options' ), array( 'type' => 'sectionend', 'id' => 'ordernumber_options' ),
// TODO: customize order password, and other numbers! // TODO: customize order password, and other numbers!
...@@ -158,10 +159,10 @@ if ( in_array( 'woocommerce/woocommerce.php', apply_filters( 'active_plugins', g ...@@ -158,10 +159,10 @@ if ( in_array( 'woocommerce/woocommerce.php', apply_filters( 'active_plugins', g
add_option ('customize_ordernumber', '0'); add_option ('customize_ordernumber', '0');
add_option ('ordernumber_format', "#"); add_option ('ordernumber_format', "#");
add_option ('ordernumber_global', '0'); add_option ('ordernumber_global', 'no');
add_option ('ordernumber_padding', '1'); // add_option ('ordernumber_padding', '1');
add_option ('ordernumber_start', '1'); // add_option ('ordernumber_start', '1');
add_option ('ordernumber_step', '1'); // add_option ('ordernumber_step', '1');
add_option ('ordernumber_variables', array()); add_option ('ordernumber_variables', array());
...@@ -712,7 +713,7 @@ if ( in_array( 'woocommerce/woocommerce.php', apply_filters( 'active_plugins', g ...@@ -712,7 +713,7 @@ if ( in_array( 'woocommerce/woocommerce.php', apply_filters( 'active_plugins', g
} }
protected function applyCustomVariables ($nrtype, $order, $reps, $customvars) { protected function setupCustomVariables ($nrtype, $order, $reps, $customvars) {
foreach ($customvars as $c) { foreach ($customvars as $c) {
$conditionvar = strtolower($c['conditionvar']); $conditionvar = strtolower($c['conditionvar']);
$op = $c['conditionop']; $op = $c['conditionop'];
...@@ -770,14 +771,8 @@ if ( in_array( 'woocommerce/woocommerce.php', apply_filters( 'active_plugins', g ...@@ -770,14 +771,8 @@ if ( in_array( 'woocommerce/woocommerce.php', apply_filters( 'active_plugins', g
return $reps; return $reps;
} }
protected function doReplacements ($fmt, $reps) {
// First, replace all random...[n] fields. This needs to be done with a regexp and a callback:
$fmt = preg_replace_callback ('/\[(random)(.*?)([0-9]*?)\]/', array($this, 'replaceRandom'), $fmt);
return str_ireplace (array_keys($reps), array_values($reps), $fmt);
}
// Allow the user to override the format like any other custom variable: // Allow the user to override the format like any other custom variable:
protected function determineNumberFormatString($fmt, $type, $order, $reps) { protected function setupNumberFormatString($fmt, $type, $order, $reps) {
if (isset($reps['['.$type.'_format]'])) { if (isset($reps['['.$type.'_format]'])) {
return $reps['['.$type.'_format]']; return $reps['['.$type.'_format]'];
} else { } else {
...@@ -785,38 +780,99 @@ if ( in_array( 'woocommerce/woocommerce.php', apply_filters( 'active_plugins', g ...@@ -785,38 +780,99 @@ if ( in_array( 'woocommerce/woocommerce.php', apply_filters( 'active_plugins', g
} }
} }
protected function doReplacements ($fmt, $reps) {
// First, replace all random...[n] fields. This needs to be done with a regexp and a callback:
$fmt = preg_replace_callback ('/\[(random)(.*?)([0-9]*?)\]/', array($this, 'replaceRandom'), $fmt);
return str_ireplace (array_keys($reps), array_values($reps), $fmt);
}
protected function extractCounterSettings ($fmt, $type, $ctrsettings) {
// First, extract all counter settings, i.e. all strings of the form [#####:startval/increment] or [####/increment:startval]
$regexp = '%\[(#+)(/([0-9]+))?(:([0-9]+))?(/([0-9]+))?\]%';
// $counters = array();
if (preg_match($regexp, $fmt, $counters)) {
// $counters is an array of the form:
// Array (
// [0] => [#####:100/3]
// [1] => #####
// [2] =>
// [3] =>
// [4] => :100
// [5] => 100
// [6] => /3
// [7] => 3
// )
$ctrsettings["${type}_padding"] = strlen($counters[1]);
if (!empty($counters[2])) {
// $counters[2] contains the whole "/n" part, while $counters[3] contains just the step itself
$ctrsettings["${type}_step"] = $counters[3];
}
if (!empty($counters[4])) {
// $counters[4] contains the whole ":n" part, while $counters[5] contains just the start value itself
$ctrsettings["${type}_start"] = $counters[5];
}
if (!empty($counters[6])) {
// $counters[6] contains the whole ":n" part, while $counters[7] contains just the start value itself
$ctrsettings["${type}_step"] = $counters[7];
}
// print("<pre>Counters regexp matches: ".print_r($counters,1)."</pre>");
// $ctrsettings["${type}_padding"] =
$fmt = preg_replace($regexp, "#", $fmt);
} else {
// print("<pre>No counters match the regexp '$regexp' in the format '$fmt'</pre>");
}
// Replace all extended counter definitions by a single #
// Split at a | to get the number format and a possibly different counter increment format
// If a separate counter format is given after the |, use it, otherwise reuse the number format itself as counter format
$parts = explode ("|", $fmt);
$ctrsettings["${type}_format"] = $parts[0];
$ctrsettings["${type}_counter"] = ($ctrsettings["${type}_global"]=='yes')?"":$parts[(count($parts)>1)?1:0];
// print("<pre>Counter settings are: ".print_r($ctrsettings,1)."</pre>");
return $ctrsettings;
}
/* replace the variables in the given format. $type indicates the type of number, currently only 'ordernumber', because WooCommerce does not support invoices or customer numbers. We might allow the shop owner to customize the order password, though. */ /* replace the variables in the given format. $type indicates the type of number, currently only 'ordernumber', because WooCommerce does not support invoices or customer numbers. We might allow the shop owner to customize the order password, though. */
function replace_fields ($fmt, $type, $order, $customvars) { function createNumber ($fmt, $type, $order, $customvars, $ctrsettings) {
$reps = $this->setupReplacements ($type, $order); $reps = $this->setupReplacements ($type, $order);
$reps = $this->applyCustomVariables ($type, $order, $reps, $customvars); $reps = $this->setupCustomVariables ($type, $order, $reps, $customvars);
$format = $this->determineNumberFormatString($fmt, $type, $order, $reps); $format = $this->setupNumberFormatString($fmt, $type, $order, $reps);
return $this->doReplacements($format, $reps); $format = $this->doReplacements($format, $reps);
$ctrsettings = $this->extractCounterSettings ($format, $type, $ctrsettings);
$countername = $ctrsettings["${type}_counter"];
// Look up the current counter
$count = $this->_getCounter($type, $countername, $ctrsettings["${type}_start"] - $ctrsettings["${type}_step"]) + $ctrsettings["${type}_step"];
$this->_setCounter($type, $countername, $count);
// return the format with the counter inserted
$number = str_replace ("#", sprintf('%0' . $ctrsettings["${type}_padding"] . 's', $count), $ctrsettings["${type}_format"]);
return $number;
} }
function create_ordernumber($orderid, $order, $type='ordernumber') { function create_ordernumber($orderid, $order, $type='ordernumber') {
if (get_option('customize_'.$type, 'false')) { if (get_option('customize_'.$type, 'false')) {
$fmt = get_option ($type.'_format', "#"); $fmt = get_option ($type.'_format', "#");
$global = get_option ($type.'_global', 1); $ctrsettings = array(
$padding = get_option ($type.'_padding', 1); "${type}_format" => '',
$step = get_option ($type.'_step', 1); "${type}_counter" => '',
$start = get_option ($type.'_start', 1)-$step; // The counter contains the PREVIOUS number! "${type}_global" => get_option ($type.'_global', 'no'),
"${type}_padding" => 1,
"${type}_step" => 1,
"${type}_start" => 1,
// "${type}_padding" => get_option ($type.'_padding', 1),
// "${type}_step" => get_option ($type.'_step', 1),
// "${type}_start" => get_option ($type.'_start', 1),
);
$customvars = get_option ('ordernumber_variables', array()); $customvars = get_option ('ordernumber_variables', array());
$nr = $this->replace_fields ($fmt, $type, $order, $customvars); $number = $this->createNumber ($fmt, $type, $order, $customvars, $ctrsettings);
// Split at a | to get the number format and a possibly different counter increment format
// If a separate counter format is given after the |, use it, otherwise reuse the number format itself as counter format
$parts = explode ("|", $nr);
$format = $parts[0];
$counterfmt = ($global==1)?"":$parts[(count($parts)>1)?1:0];
// Look up the current counter
$count = $this->_getCounter($type, $counterfmt, $start) + $step;
$this->_setCounter($type, $counterfmt, $count);
// return the format with the counter inserted
$number = str_replace ("#", sprintf('%0' . $padding . 's', $count), $format);
update_post_meta( $orderid, $this->ordernumber_meta, $number ); update_post_meta( $orderid, $this->ordernumber_meta, $number );
return $number; return $number;
} else { } else {
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment