TestRail.pm 5.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150
  1. # ABSTRACT: Upload your TAP results to TestRail in realtime
  2. # PODNAME: App::Prove::Plugin::TestRail
  3. package App::Prove::Plugin::TestRail;
  4. use strict;
  5. use warnings;
  6. use utf8;
  7. use File::HomeDir qw{my_home};
  8. use TestRail::Utils;
  9. =head1 SYNOPSIS
  10. `prove -PTestRail='apiurl=http://some.testrail.install/,user=someUser,password=somePassword,project=TestProject,run=TestRun,plan=TestPlan,configs=Config1:Config2:Config3,version=0.014' sometest.t`
  11. =cut
  12. =head1 DESCRIPTION
  13. Prove plugin to upload test results to TestRail installations.
  14. Accepts input in the standard Prove plugin fashion (-Ppluginname='key=value,key=value,key=value...'), but will also parse a config file.
  15. When fed in prove plugin style, key=value input is expected.
  16. If \$HOME/.testrailrc exists, it will be parsed for any of these values in a newline separated key=value list. Example:
  17. apiurl=http://some.testrail.install
  18. user=someGuy
  19. password=superS3cret
  20. project=TestProject
  21. run=TestRun
  22. plan=GosPlan
  23. configs=config1:config2:config3: ... :configN
  24. version=xx.xx.xx.xx
  25. step_results=sr_sys_name
  26. lockname=internal_lock_name
  27. testsuite_id=123
  28. testsuite=blahblah #don't do this it's mutually exclusive with testuite_id
  29. sections=section1:section2:section3: ... :sectionN
  30. autoclose=0
  31. encoding=UTF-8
  32. configuration_group=Operating Systems
  33. test_bad_status=blocked
  34. max_tries=3
  35. Note that passing configurations as filters for runs inside of plans are separated by colons.
  36. If a configuration_group option is passed, it, and any configurations passed will be created automatically for you in the case they do not exist.
  37. Values passed in via query string will override values in \$HOME/.testrailrc.
  38. If your system has no concept of user homes, it will look in the current directory for .testrailrc.
  39. See the documentation for the constructor of L<Test::Rail::Parser> as to why you might want to pass the aforementioned options.
  40. =head1 CAVEATS
  41. When running prove in multiple job mode (-j), or when breaking out test jobs into multiple prove processes, auto-spawn of plans & runs can race.
  42. Be sure to extend your harness to make sure these things are already created if you do either of these things.
  43. Also, all parameters expecting names are vulnerable to duplicate naming issues. Try not to use the same name for:
  44. * projects
  45. * testsuites within the same project
  46. * sections within the same testsuite that are peers
  47. * test cases
  48. * test plans and runs outside of plans which are not completed
  49. * configurations & configuration groups
  50. To do so will result in the first of said item found.
  51. This might result in the reuse of an existing run/plan unintentionally, or spawning runs within the wrong project/testsuite or with incorrect test sections.
  52. Similarly, duplicate named tests will result in one of the dupes never being run (as the first found is chosen).
  53. =head1 OVERRIDDEN METHODS
  54. =head2 load(parser)
  55. Shoves the arguments passed to the prove plugin into $ENV so that Test::Rail::Parser can get at them.
  56. Not the most elegant solution, but I see no other clear path to get those variables downrange to it's constructor.
  57. =cut
  58. sub load {
  59. my ($class, $p) = @_;
  60. my $app = $p->{app_prove};
  61. my $args = $p->{'args'};
  62. my $params = {};
  63. #Only attempt parse if we aren't mocking and the homedir exists
  64. my $homedir = my_home() || '.';
  65. $params = TestRail::Utils::parseConfig($homedir) if -e $homedir && !$ENV{'TESTRAIL_MOCKED'};
  66. my @kvp = ();
  67. my ($key,$value);
  68. foreach my $arg (@$args) {
  69. @kvp = split(/=/,$arg);
  70. if (scalar(@kvp) < 2) {
  71. print "Unrecognized Argument '$arg' to App::Prove::Plugin::Testrail, ignoring\n";
  72. next;
  73. }
  74. $key = shift @kvp;
  75. $value = join('',@kvp);
  76. $params->{$key} = $value;
  77. }
  78. $app->harness('Test::Rail::Harness');
  79. $app->merge(1);
  80. #XXX I can't figure out for the life of me any other way to pass this data. #YOLO
  81. $ENV{'TESTRAIL_APIURL'} = $params->{apiurl};
  82. $ENV{'TESTRAIL_USER'} = $params->{user};
  83. $ENV{'TESTRAIL_PASS'} = $params->{password};
  84. $ENV{'TESTRAIL_PROJ'} = $params->{project};
  85. $ENV{'TESTRAIL_RUN'} = $params->{run};
  86. $ENV{'TESTRAIL_PLAN'} = $params->{plan};
  87. $ENV{'TESTRAIL_PLAN_ID'} = $params->{plan_id};
  88. $ENV{'TESTRAIL_CONFIGS'} = $params->{configs};
  89. $ENV{'TESTRAIL_VERSION'} = $params->{version};
  90. $ENV{'TESTRAIL_STEPS'} = $params->{step_results};
  91. $ENV{'TESTRAIL_SPAWN'} = $params->{testsuite_id};
  92. $ENV{'TESTRAIL_TESTSUITE'} = $params->{testsuite};
  93. $ENV{'TESTRAIL_SECTIONS'} = $params->{sections};
  94. $ENV{'TESTRAIL_AUTOCLOSE'} = $params->{autoclose};
  95. $ENV{'TESTRAIL_ENCODING'} = $params->{encoding};
  96. $ENV{'TESTRAIL_CGROUP'} = $params->{'configuration_group'};
  97. $ENV{'TESTRAIL_TBAD'} = $params->{'test_bad_status'};
  98. $ENV{'TESTRAIL_MAX_TRIES'} = $params->{'max_tries'};
  99. return $class;
  100. }
  101. 1;
  102. __END__
  103. =head1 SEE ALSO
  104. L<TestRail::API>
  105. L<Test::Rail::Parser>
  106. L<App::Prove>
  107. L<File::HomeDir> for the finding of .testrailrc
  108. =head1 SPECIAL THANKS
  109. Thanks to cPanel Inc, for graciously funding the creation of this module.