I was trying to look for some kind of UK (Royal Mail) postage API with no success, then looked for some kind of server side script to handle postage for me (Perl, PHP, ASP etc) also with no success. Therefore I decided I would write my own script from scratch. This also had the benefit of being able to use my own custom rates.

- My main issue is regarding my data, which I have seemed to over complicate, so when it comes to creating 1) an admin feature to update it, 2) an overview, to display in a neatly formatted table the postage rates for each location - I may have difficulty (any idiot must be able to use it). I tried to create the data to be as compact as possible i.e. using a multiplier system where consecutive rates are part of a "pattern".

- Another issue is my use of infinity, whats the point in even entering a system of loops, when the postage cost never changes. Maybe I should try to recognize when it gets to a stage like this, for efficiency purposes.

- Finally, I also have the issue that I have to account for the possibility of a huge weight input, and since theres a size limit (20000g national, 2000g international) I would need to repeat i.e. so orders can be split up into seperate packages. I'm sure I won't have difficulties doing this (maybe use an inner subroutine, or even try out the redo command), but before doing so I wanted some advice in improving my script.

If anyone has done something like this before, or has any advice, could they please help me out a little. Maybe a pointer to a free quality pre-written script. Or just some feedback on my script. By the way, modules are out of the question, since i'm unable to install them onto my web server.

Here is what I have come up with so far, it still needs a little work in its current state (ignore my questionable cost operations, I was just playing around):

I'd like to be able to help you, but unfortunately it's rather impossible to decipher what your intent is by your code or your description.

It'd also be helpful if the code didn't kill the wrapping of your description, and that would be helped if you didn't use the list assignment when saving your regex captures. It's rather difficult to read what is assigned where when you use that form, so I'd strongly advise that you rewrite your code as the following:

To put it simply, I need to write a function that will allow me to calculate the postage cost based on the weight of an order, using my own custom rates. Since I was unable to find anything suitable by searching, I started to write my own function, but I think i'm probably going the wrong way about it. Maybe some advice how somebody else would go about it is what i'm after. My original post was kind of a bunch of my thoughts/notes so I apologise if it wasn't clear enough.

I also apologise for my style of coding, its how i've always written it, and my brain is good at reading it like that too. To be honest I never knew why my message sometimes didn't wrap. Also, you'll see that $d contains a part of a regex for a "decimal" number, which accounts for the 8 "missing" captures.

I'm on holiday at the moment, but I planned on just continuing as I was, attempting to refine my function until it does everything I require, and not worry about the format of the data. But surely this is something many ecommerce developers have had to produce, and i'm here re-inventing the wheel.

I very much want to help you, but I would need you to explain in words what the rules you're trying to accomplish for calculating the postage. I believe that I have your code mostly deciphered now that you explained about the $d, and I definitely have a lot of things I could say about the approach.

Nevertheless, I'm going to focus on some smaller issues right now. Your delimiters for the data is very much not doing you any favors. Obviously this is a custom job, so you can do what you want. But it makes since to use a format that makes the code easier to read.

To that end, I suggest you use paragraph mode and delimit the different sections with double returns. This lets you list the different ranges one after another in a much easier to read format.

Additionally, I would strongly suggest that you redefine your ranges as something like "$minvalue to $maxvalue" instead of having them be include a length of the range and using the greater sign in a weird way.

Finally, if you don't want a specific grouping in a regex to captuer anything, use (?: ... ) instead of ( ... ). You had 3 different areas where you were saving teh decimal of a number only because you wanted it to be optional.

Anyway, I've only exercised some of these changes in the following bit of code. Hopefully, some of the refactoring will be helpful to you:

Thanks very much for all your effort. I've looked through your code and I like the improvements that you have made.

The new data format is much nicer. As this function will become part of a few other existing functions, I had originally wanted to keep the data in the same format as those. Since no one would ever need to read the data in its raw format, I didn't feel it was neccessary to make it readable. But I much prefer your way, as you say, it makes sense.

I did originally use ranges i.e. "1-200, 201-400, 401-600" instead of a "length", but this would mean having to use a whole other level of error checking i.e. check the right side is higher than the left side etc (me attempting to be efficient). I would very much like to go back to ranges.

I haven't delved enough into regular expressions yet, so thank you for explaining how to not capture a particular group. I never knew it was possible.

"Cost operations" allow me to most importantly make delivery free after a certain weight i.e. Europe over 10000g will be 0.00.

The most important part, which I hadn't yet got round to doing is what I explained previously, since the maximum weight for i.e. Europe is 2000g, I would need the rates to "repeat" so that i.e. order = 3000g (above the max), first package = 2000g, second package = 1000g. I planned on doing this with some kind of $weightoffset, which will restart while appending to the existing $totalcost after i.e. 2000g. I hope I have explained this properly.

Anyhow, I will continue work on your refined function tomorrow. And I would massively appreciate any help or advice as you have done so already, its very helpful to see how others refine what i've done.

The following is meant to be a proof of concept, and not a finished product.

Basically, I would suggest that you remove the need for a special markup language from your script entirely. It needless complicates the code and makes it much harder to use in my opinion. Take advantage of the fact that you know perl and code your more complicated equations in perl as well.

I still left the below with the configuration info in the __DATA__ block, but that's not strictly necessary either. You could just as easily hardcode the config data directly in a hash that would remove the need for parsing.

Firstly, my apologies for bumping this post back up. A couple of months ago, without going into too much detail, there were a few personal issues in my life, and I was forced to abandon my efforts on this project as well as others. On the upside, I kick started my career a couple of weeks ago, and started my first ever full time job as a junior Perl software/web application developer, which is something I have dreamed of becoming since I was 14. Its going pretty well, although one of my first tasks involves parsing largely variable XML structures into a standardized Perl data structure, which is proving to be tricky, but my use of XPath seems to be successful so far!

Anyway, I just wanted to let you know that your help was invaluable and I was able to use your code examples to produce a working "postage cost" function (although there are still a couple things I need to adapt before implementing it live). Your efforts will/have played a huge role in increasing worldwide sales through one of my ecommerce websites.

Thank you very much, and my apologies once again for my delayed response.