2014-02-18 121 views
2

我正在嘗試爲此perl模塊函數編寫一些單元測試,但我遇到了一些環境變量問題。我將首先列出這些文件,然後更詳細地解釋這個問題。在Perl單元測試期間更改環境變量

processBuildSubs.pm

package processBuildSubs; 
use strict; 
use warnings; 
use LWP::UserAgent; 
use HTTP::Request::Common; 
use HTTP::Status; 

# Declare environment variables used in this package that are needed 
use constant URI_BASE  => $ENV {"URI_BASE"}; 
use constant URI_RESOURCE => $ENV {"URI_RESOURCE"}; 

# Shell Environment Related Constants visible. 
# Make visible. 

our $URI_BASE = URI_BASE; 
our $URI_RESOURCE = URI_RESOURCE; 

sub populatePartitions 
{ 
    # Define locals 
    my $url; 
    my $ua = new LWP::UserAgent; 

    $url = "$URI_BASE"."$URI_RESOURCE"."/some/path"; 

    # Make a request to the $url 
    $res = $ua->request (GET $url); 

    if ($res->code() != HTTP::Status->RC_OK()) 
    { 
    # The request didn't return 200 OK so it's in here now. 
    } 
    else 
    { 
    # The request returned 200 OK, so now it's here. 
    } 
} 

我希望能夠單元測試既if pathelse path,但是,它會如果我沒有需要改變processBuildSubs.pm代碼是最適合我在所有。這是一個我目前無法控制的外部文件。我只負責單元測試(儘管我明白如果我們也可以更改源代碼,它可以更有效地進行測試)。

因此,爲了測試兩條路徑,我們需要相應地設置環境變量URI_BASEURI_RESOURCE,以便請求失敗一次,並且成功一次。 (我是有興趣學習如何存根出在將來的時間這個電話,但那是預留給另一個問題)

這是我的測試文件:

processBuildSubs.t

use strict; 
use Test::More qw(no_plan); 

BEGIN { use_ok('processBuildSubs') }; 

# Test 1 of populatePartitions() function 
my $processBuildProdsCall = processBuildSubs::populatePartitions(); 
is($populatePartitionsCall, 0, "populatePartitions() Test for 0 Val Passed"); 

# Test 2 of populatePartitions() function 
# I need to change some environment variables that processBuildSubs depends on here. 
my $processBuildProdsCall = processBuildSubs::populatePartitions(); 
is($populatePartitionsCall, 0, "populatePartitions() Test for 0 Val Passed"); 

我們現在正在改變環境變量的最好的嘗試是使用像這樣的外部shell腳本(但是,在上述文件中的my調用之間改變它們是理想的):

run_tests.sh

#!/bin/bash 

# Run the tests once 
perl ./BuildProcess.pl 
perl ./Build testcover # Ultimately calls the processBuildSubs.t test file 

# Now export some variables so the other test passes. 
export URI_BASE="https://some-alias/" 
export URI_RESOURCE="some-resource" 

# Then run the test suite again with the env set so the else condition passes. 
perl ./BuildProcess.pl 
perl ./Build testcover 

正如你所看到的,這將是做事的好方法,因爲我們每次運行整個測試套件與不同的環境。理想情況下,我們希望在測試之間儘可能在processBuildSubs.t文件中設置我們的環境。

請讓我知道,如果我可以提供任何進一步的信息。

+0

你可以用寫在Perl中的腳本替換'run_tests.sh',所以'%ENV'的改變會影響子PID。 –

+0

你可以使用Class :: Unload? – ikegami

回答

0

你是否反對爲單獨的測試環境分開腳本?

# processBuildSubs.t 
BEGIN { 
    @ENV{"URI_BASE","URI_RESOURCE"} = ("https://some-alias/","some-resource"); 
} 
use Test::More; 
... tests go here ... 

# processBuildSubs-env2.t 
BEGIN { 
    @ENV{"URI_BASE","URI_RESOURCE"} = ("https://another-alias/","another-resource"); 
} 
use Test::More; 
... tests go here ... 

通過在BEGIN塊設置%ENV,加載任何其他模塊之前,您做出不同的環境變量在編譯時提供給您的其他模塊。

+0

嗯,這不是一個壞主意,我想我只是擔心我會得到一百萬個額外的文件。但這是一個很好的計劃。我會考慮一下。 – ardavis