Dec 6, 2012

Override DNS on a Linux system without root

I had this problem for a long time, and no one ever proposed a good solution. Recently I got a new answer on my, almost 2 year old, Unix and Linux StackExchange question. This information seems very obscure and so I thought I'd share it, if you too have had this problem and were unable to find this, or at least found finding it hard, consider upvoting the answer.

Problem

You're using a Linux system that you don't have root on, you need to override the DNS of the system. You usually want to do this because you're testing a service (web site) that does not have a proper hostname, but needs one in order to function properly. In the hosting world this comes up often enough.

Solution

You can set the HOSTALIASES environment variable before running your client program. HOSTALIASES is an environment variable that points to a file that is essentially alias value pairs.


$ echo "foo www.google.com" > ~/my_hosts
$ HOSTALIASES=~/my_hosts wget foo
See hostname(7).

Nov 7, 2012

Business::CyberSource API is stabilizing as of 0.7.x

Business::CyberSource (BC) has been going through API changes for a while now. If you're using it you've probably noticed this and wondered why? The reason behind it was when I first made it I wanted it to be extremely simple to use, and I was realistically a Junior programmer. Over the past year I learned a lot about API design and Object Oriented Programming, as well as payment gateways and credit card transaction processing. From the first production ready release I knew that it had design problems due to a large quantity of duplicated code, but at the time I didn't know how to get rid of it.

Domain Driven Design

My first refactor used some principles I learned from Domain-Driven Design: Tackling Complexity in the Heart of Software I changed the design of the objects to be more clear for experts in CyberSource. I also started restructuring them to more closely match the remote model. This meant making Requests and Responses to be made up of nested objects (Responses were only done as of 0.7.x). Another Change regarding this was to rename the submit method to run_transaction which is the name of the Remote Procedure call that is executed.

Composite Design Pattern

By making the Requests up of nested objects it allowed me to use the Composite Pattern from Design Patterns: Elements of Reusable Object-Oriented Software to serialize all of the objects into a simple nested hashref that XML::Compile::SOAP expects. Moving to these smaller objects that could serialize allowed me to also add more offline tests.

Dependency Injection in Tests

Most of the tests for BC start out exactly the same, except for one change, the value in the amount part of the Credit Card Authorization. This is because CyberSource's Test API uses special amounts to allow you to test getting different responses. e.g. something like (I'd have to look it up) 5000.05 is maybe a REJECT with a special processor code and cv code. Because of this I wired up my tests using Bread::Board to reduce the amount of boilerplate code in all tests that require actual remote interaction.

The Impact

Ultimately changing my Remote Facade to make use of more design patterns and be designed after it's niche domain has allowed me to have both simpler, deduplicated, more robust, more correct, and easier to modify code. Some things were not possible in earlier versions, or would have been incredibly complex to add. Now it'll simply be an issue of adding a Moose attribute to add a feature present in the WSDL. Before certain calls could not return all of information that was in the actual SOAP response, now everything should be accessible.

Possible Bugs

One of the possible bugs of this last refactor is that I use MooseX::StrictConstructor for all of my Moose objects. It is possible now that the XML::Compile::SOAP hash is simply passed to the Response Object that if a key I didn't account for were present that an exception would be thrown. If this is thrown on anything other than a 102 Invalid Field response, then it is a bug in BC and should be reported. I could have turned StrictConstructor off on the responses, but I believe that throwing the exceptions may ultimately make BC a better library. Also with a test suite that totals over 1400 (including generated generic ) tests, I'm fairly confident that there will be no problems in production.

New Debugging

In order to aid in finding bugs and diagnosing problems when they happen cybersource now has 2 debug setting levels. These can be set by having debug be 0 (off), 1 (request/response hash), 2 (full soap payloads). These should not be turned on in production and because they will print out Credit Card numbers.

In Trial

Currently I've left BC v0.7.5 in trial, but barring any bugs being reported, or cpan testers tests failing, I'll probably release v.0.7.6 as stable early early next week.

Stable API

I do not forsee any more major API changes in the future of BC, all of my original problems have been weeded out. This means I'll be able to focus on features and documentation with future work. It is possible that some changes to exceptions and error handling may happen, but I don't see that being a big issue.

Nov 3, 2012

Interface Driven Design

What is Interface Driven Design?

Interface Driven Design simply means that you should design your software around a flexible, easy to use, easy to understand interface. This is easy to achieve if your objects are of SOLID design. There is a simple table and reference link if you're not familiar with the principles.

My Work is SOLID already

Then you're on the right track but it's not enough if you don't fully marry the concept to best practices. I've seen quite a bit of work that's SOLID enough but fails to provide good interfaces.

Why is this so important?

Getting your interfaces correct is important because someone should be able to replace your code with new code, or subclassed code and it should still work.

Example: LWP::UserAgent and Mojo::Useragent

These two libraries do exactly the same thing, they provide an HTTP Client. However, they do not conform to the same interface. This means That if you're using Mojolicious to write a web application, but require an external library to interface with a remote API, because its interface will make your development easier, you cannot change it's use of LWP::UserAgent to Mojo::Useragent. Now you've added another dependency and complexity to your application.

Example: DBI

DBI is an example of a common interface to many different database drivers that do similar things, but underlyingly with different syntax. This allows you to use a common interface and ignore the differences in implementation between, say DBD::mysql and DBD::Pg.

How do I get there?

To begin, and as a general rule your interface should conform to style choices in the language you're using. Meaning that in Perl you should use $obj->foo_bar not $obj->getFooBar as it is the style most objects use.

Domain Driven Design

The first thing I suggest doing is design your initial interface using Domain Driven Design. Look at the common language used to describe the thing that you're building, and name your package, classes, methods, functions, after words from the common language. You're writing a new HTTP client? you probably have some concept of POST, so $client->post makes a lot of sense. If you're writing a billing system you may have some concept of Invoice->process. When doing Domain Driven Design your Interface should be easy to understand by an Expert in that domain (regardless of whether they are technically savvy ). Example if I told a Billing expert I was writing the code for Invoice->process they probably would have no idea what the internals meant, but they should easily understand the purpose and a general idea of what it actually does. (note: having an Invoice object might be bad, as an invoice is a request for payment on a Sale, and a receipt is a record of, therefore they are just views on a Sale, but that's a more complex notion)

Pure Fabrication

Unfortunately sometimes what you're creating has no real world equivalent (actually HTTP is an example that is now more of its own domain). So you're making it up as you go. In this case you need to create objects that are a Pure Fabrication. When creating interfaces for these I suggest looking to patterns, simple interfaces, and the interfaces for similar things in other projects, or languages. Use names that are as descriptive as you can get.

Existing Interfaces

You want to do this whenever there is an existing implementation that's not good enough, but has a decent interface. Perfect examples are DBI and LWP. They both have good interfaces, but there's a chance that the implementation isn't good enough (or you have need of a nonexistant driver).

An example with be AnyEvent::HTTP::LWP::UserAgent. If you're using AnyEvent you'll probably know you don't want LWP's blocking interface, but unfortunately the library you need to use uses LWP, what a dilemma. You could rewrite the library entirely to use AnyEvent::HTTP, but this will be both tedious and error prone. However, Anyevent::HTTP::LWP::UserAgent provides an LWP Interface, this means that you can simply substitute it in the library (hopefully the library made this easy by following the Inversion of Control Principle to be discussed in a future post).

Like AnyEvent::HTTP::LWP::UserAgent you may need to build a Facade interface that mimicks another interface. It would be better to start with this interface, but then again sometimes that's not ideal either.

Combinations

Sometimes you have to combine all of these strategies. Business::OnlinePayment::CyberSource (BOPC) and Business::CyberSource ( things I'm responsible for ) are good examples. Business::CyberSource was written because BOPC 2.x was no longer maintained and relied on a proprietary library which was not 64 bit compatible. I decided that I did not like the Business::OnlinePayment interface (and still don't to be honest ) and so set out to create a new one.

My first attempts was in retrospect focussed more on creating a perlish API than a Model driven API. In the long run this caused significant pain and resulted in some bad code. As of version 0.7.x (in TRIAL) Business::CyberSource's API is modeled after the remote API that CyberSource provides, and as such it has become much easier for me to provide access to new remote API features. Because I have continued work on ensuring that my Interface only relies on it's own interfaces it should now be trivial to replace any single piece of Business::CyberSources API. Don't want to use my request objects? you could simply pass an object that can serialize to a hashref that looks like what XML::Compile::SOAP expects. Any Expert at CyberSource should be able to read and understand my API (not tested), where they might not understand BOPC's. Unfortunately to get to this point I've had to break my interface several times.

Later due to new business concerns we had a need to conform to Business::OnlinePayments Interface, and so we rewrote BOPC to use Business::CyberSource as the backend. It does not provide access to all of the features, but it can be used in anything that knows how to use a Business::OnlinePayment API. I would have preferred to have this done sooner, but due to tuits and business constraints it was put off.

If you read the Source of either of these you will find a few fabrications, such as the use of Factories.

Interface as a Language Feature

Many languages support specifying the interface via a language feature. If your language supports this you should take advantage of it. Unfortunately Perl's simple can support really isn't enough, and Moose's Interface as Role support doesn't really work due to ordering issues. (I implemented the interface but unfortunately due to ordering my implementation is runtime and happens comes after the compiletime requirement ). I will say though that I believe it is more important to provide the actual calling convention in a dynamic language like Perl, than use of an actual interface. At least with Moose I feel that an interface is (generally) as concrete as the isa for the class, and so I don't bother checking them, they are an implementation detail.

Conclusion

Ultimately the goal is to create easy interfaces to understand, use, and properly reflective of the problem. By doing so you also make concrete implementations easy to update and reuse without breaking your clients.

Sep 5, 2012

UML Tools

Why UML?

Many people appear to think that modelling is only for academic textbooks and school. Several months ago I worked on a project that failed, for numerous reasons, but some of the reasons were mine. So I set out to figure what it was that I didn't know, that would have allowed me to build this system I had been asked to.

After reading Patterns of Enterprise Application Architecture, Domain-Driven Design: Tackling Complexity in the Heart of Software, and Design Patterns: Elements of Reusable Object-Oriented Software and realizing that all of the great books used UML. I realized that UML is a great visualization tool, and that it helped me understand the concepts they were talking about. This didn't have to be entirely academic, and perhaps I could use these tools to communicate my idea's. So I've set out to learn UML, and picked up copies of UML Distilled: A Brief Guide to the Standard Object Modelling Language (3rd Edition) and although I find it to be a decent reference guide, I didn't think it was quite what I was looking for. So I then picked up Applying UML and Patterns: An Introduction to Object-Oriented Analysis and Design and Iterative Development (3rd Edition) , and am about halfway through it. What I really wanted was a book to explain the what, when, and why of UML, this book seems to do that and more. It covers a lot of subjects I've glanced over previously in a fair amount of depth, and puts them together.

So how does using UML relate to my original issue? I determined after reading these books that what we had done poorly in our "Agile" process was planning. Another common fallacy is that iterative development means don't plan. No what it means is keep your planning to a minimum, code, code, code, plan, code, code, code, etc. If you spend more than a week planning you're spending too much time, and your planning itself should be iterative, meaning go back and do more at the beginning of each iteration. I also learned that part of, pre-coding, planning is modelling. When you're dealing with a simple one or two objects modelling is likely overkill, but as your software complexity increases, the more indispensable modelling becomes.

Armed with new theories of Object Oriented Analysis and Design, and a visual modelling language to assist I set out to model the complex system. The initial tool I selected for modelling is fairly common, and I used it to build a few diagrams, but as time went on my diagrams changed more and more, and became more complex, and I became more and more frustrated with the tools ability to help me update the model. In spite of this as I worked through the model, and distilled it, I realized that the model itself was working. Now I simply needed a better tool to model with, and more time to build the system.

What am I looking for?

I work entirely in a Linux Environment and do not have WINE set up because I abandoned Windows about 5 years ago now, so whatever tool I choose has to work in Linux, and I will only do so through WINE if no adequate non wine solutions present themselves.

I really need reasonable pricing because I'm still hemorrhaging money on student loan. Free is obviously ideal, but I need to be reasonable, this thing should not cost more than my cell phone.

I don't really use IDE's such as Eclipse or Netbeans, so integration or as a plugin is not required, in fact I don't want to run those to run this.

The first tool I used, I ultimately realized that it was making me do vector graphic artist level tweaks to make it look good. So I require that it require as little human intervention as possible to look good.

One of my colleagues is blind, and I'd like to be able to share my diagrams with him, so I require the diagram be able to be output to a simple text format. Ideally a format generated from the diagram, and not the diagram generated from the format, because while diagramming I am thinking visually.

Full UML 1.4 support is required for me to get off the ground, but I'd personally prefer UML 2.X support as it has a few nice features such as sequence diagram conditionals.

The tool should be as intuitive (to me) as possible. I've found many of the tools require my brain to context switch, or I simply have trouble finding out how to do the feature I'm looking for.

Once I discovered that some tools were capable of determining that some elements were related across diagrams I decided that I should have this feature and it should do as much for me as it can.

The tool and it's UML should be aesthetically pleasing, this seems novel, but if I hate looking at the tool I'm not going to use it.

How am I testing?

Well in addition to simply checking the general requirements I have, as you can probably tell a lot of what I'm looking for is subjective. So basically I spent some time modelling a simple blog. If I encounter any serious frustrations creating diagrams the tool is discounted and I move on. Basically this is, largely, a usability and intuitiveness test, if I have to think about the tool very much then it's getting in my way

FLOSS

Dia

The first tool I used was Dia. It is basically a free Visio clone. It's very flexible and allows me to create almost any diagram I could want, though it only seems to support UML 1.4. I also found myself micromanaging the relation lines, which only seemed to have one style and wouldn't path together in the right places. Dia requires that you click a text edit palette button to change the name on something and it's finicky about it, which is just frustrating. There was also no auto arrange feature. Ultimately I've found the unlimited flexibility to take my mind off my task of modelling and put it more on drawing. I worked with this tool for a few weeks, but these were also weeks where I was less familiar with UML, so I hit the limits later.

UMLet

UMLet was the next UML tool I tried. I found it to be much simpler than Dia for the same purpose, and it allows you to modify the elements that you can add in a purely textual way, and the file format stores them this way, which would almost provide my textual format requirements. However I found it's support for sequence diagrams to be limited. Also Class, and other diagrams would not resize if the text was too big. Lastly, although I could drag main elements out of the sidebar to add, I found that I couldn't do so with relationship lines, which got frustrating. The Class to edit class text requires a mental context switch which I found to be unpleasant.

Umbrello

Next I tried KDE's Umbrello. The first thing I noticed is that it's hideous. KDE software is usually amongst the most attractive on Linux in my opinion, but Umbrello does not follow the stereotype. The default Class is red and yellow, this can be changed but unfortunately that's not really the only problem. I found the overall user interface to be a little odd, perhaps it was just from using other tools that have some better interface design decisions. This was the first tool that I found could do cross diagram associations, and it even has a seemingly nifty feature which makes a relationship not it's own entity, and therefore you can edit it while editing the class.

Violet

Violet is actually one of the nicer open source editors, ultimately it made my top 2 pics on the Open Source list. It appeared to be relatively easy to make nice diagrams in violet, without the interface getting in the way. Unfortunately it doesn't allow diagrams to be inter related, nor does it offer any kind of a text export. I am not sure whether I ultimately like the change mouse pointer create an element on every click until you reselect the normal pointer, this is like an art tool.

ArgoUML

Argo UML is the closest to the proprietary tools I've tried. Unfortunately like all of the open source tools it only support UML 1.4. It does support cross diagram relationships, and has an easy to use interface. It is actually the originating source of one proprietary product Poseidon. However it did not support the text export. I decided to keep looking into proprietary products to see if one had a significantly better interface than this. But if you must have an Open Source product this is the one I suggest.

Web / Cloud

yUML

yUML is a partial solution to UML diagrams via a web interface. It allows you to generate most UML diagrams via a simple text interface. I like this software, it doesn't give you much control over the arrangement of the diagrams, only the semantics, but personally I think that's ok. Unfortunately it doesn't support sequence diagrams, but the author has a reason for that.

Web Sequence Diagrams

Web Sequence Diagrams is complementary to yUML, in that it provides the missing sequence diagrams, and combined you should be able to make all the UML diagrams you really need.

Creately

Creately is a flash based visio clone. To some degree I found it even nicer than Dia, because the diagrams were prettier, and mostly easier to manage. I gave up on this tool when I realized it was missing some diagrams, had not text export, and especially because I found it incredibly difficult to add multiplicity to class diagrams.

Proprietary

Visual Paradigm

I tried Visual Paradigm for UML and by tried, I mean I couldn't get it installed. I've been using Linux for ~10 years now, and half of that was on Gentoo, I even managed to get Oracle 11G working on Arch Linux, a video card that no distro could detect working, and built my own Fork. It complained of not being able to access the X server, but considering I could run other X programs from that shell, I would say that whatever it was trying to do it was trying to do wrong. I tried both the installer and the "just a zip" version, and the latters binaries didn't spawn a window. Needless to say I didn't proceed further with their software, already having a full host of alternate solutions.

Magic Draw

I was able to get Magic Draw installed, the hardest part was figuring out that they had sent my evaluation license to my email, and my email had filed it as spam. After playing with it for a while, I found that certain pieces of the diagram (again multiplicity) were hard to figure out how to add. In this case It was about how they'd named it. I felt their interface was more complicated in general than necessary. The nicest thing about Magic draw is it has the best auto arrange I've evaluated, and it does not allow elements to be placed on top of each other. However, I eliminated it due to the other challenges of its use.

Poseidon

Ok, I didn't end up trying Poseidon because by the time I got to it, I had idea's on what I was looking for. A quick look tells me that I'd have to pay more than my computer cost to get the auto arrange feature and the plugins. To try the community version I'd have to register, and it appears sign up my credit card and cancel within 30 days. I personally believe that it's shady if you're making me remember to cancel and it's not a service.

Enterprise Architect

Sparx Enterprise Architect runs in WINE I tried installing this on Wine 1.5.12, but either something went wrong with my following of the instructions, or they are not complete. Much like Visual Paradigm it isn't really worth my time to figure out why it didn't just work when I'm evaluating products. It not "just working" is a massive black mark.

Astah

Of course I save my recommendation for last. Astah Professional is very similar to ArgoUML in UI design. In addition to Argo's features it includes a working auto arrange for class diagrams, full UML 2.0 support, and a plugin to upload to yUML (untested, but should allow the textual representation). In fact during my work with it I found only a few things that I found limiting.

When using auto arrange on class diagrams any text on relation lines tends to get overlapped, but a little tweaking at that point hasn't seemed hard, and will be easier than rearrange the entire diagram. Also auto arrange doesn't seem to work for sequence diagrams. Hopefully both of these improve in future versions, but they're really minor, and I didn't find anything that was significantly better at this.

You can overlap elements, that probably shouldn't be able to overlap, such as classes and lifelines. This allows for a great deal of flexibility, but I also think that not allowing it would be a good idea, perhaps it could be a future toggle-able option. As an issue it's pretty trivial, though made a bit worse by auto arrange not working in sequence diagrams.

The only thing I don't like about it, is how, like Argo and many of the others, I have to "change my mouse pointer" to determine what new elements I'm creating, like selecting a palette. Existing model elements are drag and drop, but I wish new elements were also drag and drop as it more matches my mental model. Most of the tools I tried were this way though, only a couple being drag and drop.

Astah even appears to have a couple of reasonable pricing models, subscription, and perpetual (neither of which cost more than my phone), with cheaper for students and a free community edition. They even have a program for open source projects and community leaders called Friends of Astah.

Disclaimer: I applied for "friends" and was accepted. I was asked to write a blog on Astah. The truth is this post was already written with a winner decided before I even applied. I have refactored it a bit though to be a little more in depth on Astah.

UpdateRepublishing due to an issue with the first

Jul 24, 2012

Where's 5.16.1?

Per the 5.12 release announcement http://dev.perl.org/perl5/news/2010/perl-5.12.0.html
This release cycle marks a change to a time-based release process. Beginning with version 5.11.0, we make a new development release of Perl available on the 20th of each month. Each spring, we will release a new stable version of Perl. One month later, we will make a minor update to deal with any issues discovered after the initial ".0" release. Future releases in the stable series will follow quarterly. In contrast to releases of Perl, maintenance releases will contain fixes for issues discovered after the .0 release, but will not include new features or behavior.

5.16.0 was released on May 20, 2012, it is over 2 months later, was 5.16.0 so good that there are literally no bugs? or has something gone wrong with the time based release schedule? I also I note that there was never a 5.14.3. I'm just a concerned citizen of the Perl community, I don't want to see us go back to the days of pre 5.12, when releases happened whenever/never.

UPDATE: Per RJBS comment below, apparently there was an interesting bug in require which has just been fixed and will be getting backported.

Jun 11, 2012

Perl Core Syntax Wishlist: Role Support

I want to see Role's added, even PHP got Traits before Perl. It doesn't have to be a huge thing, in fact all I want is the composition aspect. Let me do this: I don't really want or need anything else right now, just that would be fine. We should have interfaces too, but they aren't really required just to support Role's. We should probably have some sugar like I did for class (e.g. role keyword. and some of the same modules/pragmas loaded for this too)

Jun 4, 2012

New Module: MooseX::RemoteHelper (RFC)

Background

I have spent much of the last year writing and refining Remote Facades. At this point I've worked with SOAP, REST/JSON, and RPC url-form-encoded API's. One of the hardest parts I've found is dealing with the serialization of a Data Transfer Object with a Perl interface into whatever the remote is expecting. When I started I didn't know of these patterns, or really anything about these patterns. I highly recommend reading Patterns of Enterprise Application Architecture) if you want to know more about these patterns or things like Active Record and MVC.

problem

The problems I've encountered are many, including the fact most remotes are buggy or have a cludgy interface. Though there's nothing you can do about a remote api that you don't control, you can make your local API much cleaner and more native. Doing this however comes with a few challenges. One is that you have to map a local attribute name to a remote attribute name, because Perl uses underscores, and Java uses camel case, e.g postal_code and postalCode. The second problem is that many times the value of the attribute in its perl native form is not what the remote wants, e.g. perl boolean "1" remote "Y", or a DateTime object to W3C formatting. This second is not quite the same as mapping, because mapping is one to one, this translation could be turning an array into a comma separated string. The third problem, I didn't run into until after I "solved" the first , is how should I deal with nested complex objects (one's that can't be just converted to just a string).

My first naive remote facade was very procedural and simply assembled top to bottom, in part because it was based on SOAP::Lite, and in part because I had yet to figure out a better way. This resulted in a giant unwieldy if/then chain. Obviously my translations were just inline too.

The next thing I tried was using triggers to construct a request hash to pass to XML::Compile::SOAP. This worked better as the hash constructing code was kept right next to the attribute, so if I needed to modify the local or remote attribute, I could just go look at the attribute and the trigger tied to it.

After that I tried to use a map to translate from the native attribute name to the remote attribute name. This may have been more successful had it worked more like the Assembler in the Remote Facade. But ult imately since we were developing a rapidly changing API it seemed to bog me down, this is because I was changing the attributes on both sides of the mapping and thus the mapping at the same time (so at least 3 places). Here I was just manually dealing with the translation from a W3C DateTime format to the object I needed.

a solution

When I got assigned to yet another API and found myself doing yet another mapping and translation I decided that I needed to solve the problem. Enter the first iteration of MooseX::RemoteHelper. The first tie I used it with the form-url-encoded API so it was only needed for a single level of key, value pairs. .

Once I determined how to create MX::RemoteHelper it was simply a matter of using Class::MOP::Class API's to iterate all the attributes. The source of CompositeSerialization will give you some idea of how I did this.

Then I went back to apply this to a previous module, because the technique appears to be cleaner. Unfortunately I ran into a problem, this other API was a complex data structure, and how best to provide nested hashrefs and arrayrefs. Though I was now armed with Patterns I didn't know of one that would solve the problem. Fortunately a quick flip through the Gang of Four brought me to the Composite Pattern. I used this to write the recursive CompositeSerialization so that if I had a sufficiently complex nested structure I could simply create another object to deal with that. Here's a full example:

use 5.014;
use warnings;
use Data::Dumper;

package MessagePart {
    use Moose;
    use MooseX::RemoteHelper;
    with 'MooseX::RemoteHelper::CompositeSerialization';

    has array => (
        remote_name => 'SomeColonDelimitedArray',
        isa      => 'ArrayRef',
        is        => 'ro',
        serializer => sub {
            my ( $attr, $instance ) = @_;
            return join( ':', @{ $attr->get_value( $instance ) } );
        },
    );

    __PACKAGE__->meta->make_immutable;
}
    
package Message {
    use Moose;
    use MooseX::RemoteHelper;

    with 'MooseX::RemoteHelper::CompositeSerialization';

    has bool => (
        remote_name => 'Boolean',
        isa      => 'Bool',
        is        => 'ro',
        serializer => sub {
            my ( $attr, $instance ) = @_;
            return $attr->get_value( $instance ) ? 'Y' : 'N';
        },

    );

    has foo_bar => (
        remote_name => 'FooBar',
        isa      => 'Str',
        is        => 'ro',
    );

    has part => (
        isa      => 'MessagePart',
        remote_name => 'MyMessagePart',
        is        => 'ro',
    );

    __PACKAGE__->meta->make_immutable;
}

my $message
= Message->new({
    bool    => 0,
    foo_bar => 'Baz',
    part    => MessagePart->new({ array => [ qw( 1 2 3 4 ) ] }),
});

say Dumper $message->serialize

Which should give you this data structure:

Request For Comment

I've recently released a Trial version of MooseX::RemoteHelper to CPAN. I'm currently refactoring Business::CyberSource to use it, and it appears to be solid. What I'd like to know what people think of the module names, method names and any other comments they might have. I haven't been entirely sure that I've been naming things correctly while writing this, or that the code couldn't be better in other ways. If there's functionality you wish it had but doesn't let me know.

May 28, 2012

Perl Core Syntax Wishlist: Class support

I would like to see the class keyword become part of Perl, but unlike some I don't want it simply because it's nicer syntax. I'd like it to behave differently from package. I'd basically like to see this I'm sure smarter people than I could think of a few more things that might be nice to have by default in all classes. I would like to note that method signatures is not that big of a deal to me, unless of course you want to give me named variables in the signature besides just auto shifting off self, e.g. method foo ( $bar ) { return $self->{foo} if $bar }

May 21, 2012

Better Exceptions with Exception::Base

So I've done some complaining and explaining about what I'd like to see in regards to Exceptions in Perl. I Mostly explained what I wanted for catching Exceptions, and a little on throwing Exception objects, but not really how those objects should behave. I've looked at and tried various exception modules, including croak, confess, and Throwable. I basically spent time one day reading the manuals of most of the exception objects on CPAN. Most of them didn't allow me to easily for the exceptions I needed (meaning they required more work than I thought I should do for one or two exceptions ). Among these modules I found Exception::Base, which appears to do everything I need (though I still wish for something like it in core, with shinier syntax). Of course wee need to be able to throw simple Exceptions, preferably ones that can stringify, and are easily matched in a switch or if statement. Exception::Base can do all of that, and it even boolifies to true. A really big thing I wanted was a class I could easily add attributes to without writing a whole new package/pm and subclassing it there. I wanted this because I really wanted to be able to have 2 kinds of messages, one for programmers, and one for users, but truthfully I only had one class where I needed this flexibility (at the time). It is also occasionally useful to have attributes that describe something, e.g. would be really useful in moose attribute exceptions, to be able to have an object where you could catch the exception and get the attribute name without parsing. Fortunately Exception::Base can do this too. You'll notice if you run this script that in the warn, both usermsg and logmsg are printed because they are both string_attributes. You'll also notice that attr isn't printed at all, but that we can look at it directly to make other decisions. Exception::Base has other features such as setting the verbosity so you can go from a croak level message to a full stacktrace. It also allows you to ignore_packages so that the exception does not appear to be thrown from that package. This is similar to @CARP_NOT.

May 14, 2012

Perl Core Syntax Wishlist: die should die

I hate die it is, in my humble opinion, one of the worst parts of perl. I really wish it would be deprecated, and removed, or at least replaced with something that would tell you were the code that was die-ing was being called. Replace its implementation with that of Carp's croak or confess and I'd be happy. Better yet, let's just get real exception support and deprecate die (even if that's never removed deprecation just make that real big on its pod). If you're using die please stop and use Carp, anyone using your module will thank (and by thank I mean not curse) you later.

May 7, 2012

Perl Core Syntax Wishlist: an Exception Stack

I have come to wish many things were part of Perl syntax that are not, and no using external modules is not enough for me. I think it's time Perl got the features as part of the language itself (and yes I suppose I could settle for feature.pm, and no I'm probably not going to write them myself, I'm not smart enough yet). The first of these is a proper exception stack. I want to be able to write: I think we need throw, try, catch, and finally keywords. And no I don't think it makes sense to have Object->throw. In fact I think this Original Perl 6 Syntax Proposal reads like just what we need in Perl 5. Unfortunately I think this is what we are getting in Perl 6, which IMO is not as nice.

Mar 11, 2012

Adventures with SOAP using Perl: Part 2 ( SOAP::Data::Builder )

Start by reading the first 2 parts :

  1. Part 0 Prelude (setup server.pl)
  2. Part 1 SOAP::Lite

SOAP::Data::Builder is simply a wrapper around SOAP::Data and SOAP::Serializer for SOAP::Lite. I used it because it made my life easier building nested complicated SOAP objects. However for Part 2 I will simply be showing how to use it to do the same code as Part 1. Unfortunately since Part 1 is so Simple this actually makes SOAP::Data::Builder more complex than SOAP::Lite would be for this. In a future installment I will attempt to show more complex examples, but I will explain them less. Now let's take a look at the code.

#!/usr/bin/perl
use 5.010;
use strict;
use warnings;
use SOAP::Lite +trace => [ 'debug' ];
use SOAP::Data::Builder;

my $req = SOAP::Lite->new(
    readable   => 1,
    proxy      => 'http://localhost:8877',
    ns         => 'http://namesservice.thomas_bayer.com/',
);

my $sb = SOAP::Data::Builder->new;

$sb->add_elem(
    name  => 'name',
    value => 'Mark',
);

my $res = $req->getNameInfo( $sb->to_soap_data );

say '-' x 3;

unless ( defined $res->fault ) {
    say scalar $res->valueof('//country');
} else {
    say $res->fault->{faultstring};
    say $res->fault->{detail}{error};
}

As you can see this is much the same as the final code in Part 1, and if you run it, it does exactly the same thing. The first difference you'll notice is the self explanatory creation of the SOAP::Data::Builder object. After that comes the ->add_elem method call, which will simply create an element with a given element name and a value for that element.

Once you've finished adding elements to your $sb object, then you can call pass $sb->to_soap_data to the method that you're calling on SOAP::Lite, this generates the structure that SOAP::Lite needs to be able to make your request.

The only thing I didn't like about SOAP::Data::Builder is if you don't pass the right parameters to ->add_elem it will not croak or error in any way that will really tell you what went wrong. Simple patches to this can fix it.

Mar 4, 2012

Simple scripting CLI with Expect.pm

Expect is use primarily for sending Input to Command Line programs that Prompt and wait for input. For starters you'll need an executable script and I've pasted one that I got elsewhere for a demo.

#!/usr/bin/env perl
# slightly modified from http://www.tizag.com/perlT/perluserinput.php
use 5.014;;
use warnings;


print "How old are you?";
my $age = <>;

print "What is your favorite color?";
my $color = <>;

say "You are $age, and your favorite color is $color.";
It's trivial, you should probably run it just to see what it does. Now take a look at our Expect Script.

Although you can read the comments yourself, let's go over it anyways. ->spawn takes a list of arguments, with the first being a command, and the rest being any command line arguments, or options passed to said script. I could have easily just put the command in spawn, but I though I'd show a more dynamic example. After that you'll notice I've hard coded 2 sets of params that could possibly be fed into the program. I also have created some 1 at a time iterators, this simply makes it easier to iterate them in expect. Now onto the Expect object itself.

If you've read the documentation you'll notice there are 3 debug settings, with 3 being the most verbose, and some verbose settings. None of this appeared to be as verbose as I could get, however turning on ->exp_internal(1); printed everything I needed to understand expect and debug what I was doing wrong. The ->spawn method of course forks and execs our command, the output of which then gets iterated by ->expect.

The first argument to ->expect is the timeout, which is measured in seconds. The timeout is how long expect will wait for the output to match one of the regexes. You could set it to undef if you want to wait forever, or if it's just a program that has some startup time before it prompts set it to a few seconds. The timeout will (by default) be used again in between each prompt.

After timeout you can specify a list of array refs, each of which has 2 elements. The first is a regular expression that will allow you to tell expect how to recognize a prompt. The second is a coderef which allows you to tell expect what to do if it's corresponding match is hit. Both regexes will be run against every line, checking to see if they match.

Inside of our coderef we can use ->send to send input to the prompt. Remember send doesn't automatically press enter, so be sure to add your newlines. exp_continue means after match continue using this ->expect call to try to match the next line.

When running the script you'll notice the second regex never matches, but if reading the 'internal' output you'll see that it is attempting to.

The last line is a call to ->before which in this case, not very intuitively prints everything that was in the pty after the last match, or more appropriately, before the program exited. You'll also notice that it collects the thing that you sent to the last match.

That's the basics of what I've discovered, I'm not sure I fully understand how it all works yet (which means my explanations might not be 100% correct), but perhaps me writing this will help someone else get started with Expect. Happy Hacking!