The Perl Toolchain Summit needs more sponsors. If your company depends on Perl, please support this very important event.

NAME

CodeGen::Protection::Role - Role to help rewrite parts of documents

VERSION

version 0.06

SYNOPSIS

    package CodeGen::Protection::Format::MyDocumentType;
    use Moo;
    with 'CodeGen::Protection::Role';

    our $VERSION = '0.01';    # required

    sub _tidy                {...}
    sub _start_marker_format {...}
    sub _end_marker_format   {...}

    1;

DESCRIPTION

This role allows you to easily define modules that allow you to do a safe partial rewrite of documents. If you're familiar with DBIx::Class::Schema::Loader, you probably know the basic concept.

In short, we wrap your "protected" (protected_code) code in start and end comments, with checksums for the code:

    #<<< CodeGen::Protection::Format::Perl 0.01. Do not touch any code between this and the end comment. Checksum: fa97a021bd70bf3b9fa3e52f203f2660
    
    # protected code goes here

    #>>> CodeGen::Protection::Format::Perl 0.01. Do not touch any code between this and the start comment. Checksum: fa97a021bd70bf3b9fa3e52f203f2660

See CodeGen::Protection::Format::Perl for full documentation of the OO interface, and CodeGen::Protection for full documentation of the recommended interface.

# Creating A New Protected Format

Note that this module is not suitable for protecting documents which require context outside of the protected area. JSON and YAML would be good examples of document types which are probably not suitable for this code.

Javascript, however, is excellent.

To create a new protected document package, you:

  • Create the package

  • Consume the CodeGen::Protection::Role role

  • Set the $VERSION (in \d+.\d+ format)

  • Define _start_marker_format, and _end_marker_format methods

  • Optionally define a _tidy method.

And that's it!

Let's see a concrete example using Javascript.

First, define the package:

    package CodeGen::Protection::Format::Javascript;
    use Moo;

Consume the role:

    with 'CodeGen::Protection::Role';

Set the version:

    our $VERSION = '0.01';    # required

Declare our start and end marker formats:

    sub _start_marker_format {
        '// %s %s. Do not touch any code between this and the end comment. Checksum: %s';
    }

    sub _end_marker_format {
        '// %s %s. Do not touch any code between this and the start comment. Checksum: %s';
    }

And if you have code that can tidy Javascript, you can declare a _tidy method:

    sub _tidy {
        my ( $self, $document ) = @_;
        my $tidied = ...;
        return $tidied;
    }

Regarding the start and end formats. They're separate in case we have a document type which requires separate formats. Also, for both the _start_marker_format() and the _end_marker_format(), the first '%s' is the class name and the second '%s' is version number if they're being added to the document. The second '%s' is a version regex (_version_re()) if it's being used to match the start or end marker.

The third '%s' is the md5 sum if it's being added to the document. It's a captured md5 regex ([0-9a-f]{32}) if it's being used to match the start or end marker.

And that's it! You can now read/write protected Javascript documents:

Creating:

    my $javascript = create_protected_code(
        type          => 'Javascript',
        protected_code => $sample,
    );

Or rewriting:

    my $javascript = rewrite_code(
        type          => 'Javascript',
        existing_code => $javascript,
        protected_code => $rewritten_code,
    );

AUTHOR

Curtis "Ovid" Poe <ovid@allaroundtheworld.fr>

COPYRIGHT AND LICENSE

This software is copyright (c) 2021 by Curtis "Ovid" Poe.

This is free software; you can redistribute it and/or modify it under the same terms as the Perl 5 programming language system itself.