Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Helpers for mocking and verifying statuscodes, headers etc. #23

Closed
Espenhh opened this issue Oct 14, 2013 · 7 comments
Closed

Helpers for mocking and verifying statuscodes, headers etc. #23

Espenhh opened this issue Oct 14, 2013 · 7 comments

Comments

@Espenhh
Copy link

Espenhh commented Oct 14, 2013

I've created some procedures for mocking headers and uri's, and for verifying status codes and return headers. When I write a lot of tests, this makes them easier to read.

Question 1:
Is there a possibility that these types of utility functions could be included in the TesTcl core?

Question 2:
One of my utility functions (the one named "verifyHeader" below) isn't working, it's producing this error:

Unexpected error during invocation of "verify 'Header 'Content-Type' should be 'text/plain''": rc=1, res=can't read "headerName": no such variable

Any idea what can be the cause of this error? I guess it's might be just some TCL syntax error on my part...

This is the test I've written with the procedures, and one of the tests (Isolated the procedures might seem overkill, but I've got 10-15 more of these tests...)

package require -exact testcl 1.0.2
namespace import ::testcl::*

# Comment in to enable logging
#log::lvSuppressLE info 0

proc mockUri {mockUrl} {
    on HTTP::uri return $mockUrl
}
proc mockHeader {headerName headerValue} {
    on HTTP::header $headerName return $headerValue
}

proc verifyStatusCode {statusCode} {
    verify "Status code is '$statusCode'" $statusCode eq {HTTP::status}
}
proc verifyHeader {headerName expectedHeaderValue} {
    # This one doesn't work...
    verify "Header '$headerName' should be '$expectedHeaderValue'" $expectedHeaderValue eq {HTTP::header $headerName}
}

before {
    event HTTP_REQUEST
}

it "should remove '/api' from URI" {
    mockUri "/api/users"
    mockHeader "Accept" "application/json"
    on active_members pool_api return 0

    verifyStatusCode 503
    verifyHeader "Content-Type" "text/plain"
    verifyHeader "Cache-Control" "no-cache"
    verifyHeader "X-Forwarded-SSL" "true"

    run rules/2.tcl http
}

This is the iRule:

rule http {
    when HTTP_REQUEST {
        HTTP::header insert X-Forwarded-SSL true

        if { [HTTP::uri] starts_with "/api/"} {
            if { [active_members pool_api] == 0 } {
                if { [HTTP::header Accept] contains "json" } {
                    HTTP::respond 503 content "System not availiable" Content-Type "text/plain" Cache-Control "no-cache"
                } else { 
                    HTTP::redirect "http://errorsite.com" 
                }
            } else {
                set newuri [string map {/api/ /} [HTTP::uri]]
                HTTP::uri $newuri
                pool pool_api
            }
        } else {
            if { [active_members pool_backend] == 0 } {
                HTTP::redirect "http://errorsite.com"
            } else {
                pool pool_backend
            }
        }
    }
}
@landro
Copy link
Owner

landro commented Oct 14, 2013

Regarding nr 1. - why not. It would probably make sense to put it into a custom testcl namespace ::testcl::utils. Could you provide a pull request containing:

  1. Well - the code
  2. Some tests and examples
  3. Some nice documentation in Readme.md

Regarding nr. 2 - could you please try rename headerName into something else - it might shadow a global variable or something @Sebastian-Brzuzek, what do you think?

BTW, we should try to use the google group for discussing before opening tickets: https://groups.google.com/forum/#!forum/testcl-user

@Sebastian-Brzuzek
Copy link
Contributor

I can't see any benefit with ready to use mock functions - almost the same amount of writing and no additional functionality.
I agree that verify procedures could be expanded a little bit. But I'm not sure if this is reasonable to add this to the core of TesTcl. It could be reasonable to add some optional methods to support most common verification cases, but it will be tricky to define if something is common.
We have to keep balance between amout of provided procedures, flexibility and complexity.

@Espenhh what about using this kind of test script in your case?

package require -exact testcl 1.0.2
namespace import ::testcl::*

# Comment in to enable logging
#log::lvSuppressLE info 0

proc verifyEq {what expected calculated} {
    verify "$what is '$expected'" $expected eq $calculated
}

before {
    event HTTP_REQUEST
}

it "should remove '/api' from URI" {
    HTTP::uri "/api/users"
    HTTP::header "Accept" "application/json"
    on active_members pool_api return 0

    verifyEq "Status code" 503 {HTTP::status}
    verifyEq "Header Content-Type" "text/plain" {HTTP::header "Content-Type"}
    verifyEq "Header Cache-Control" "no-cache" {HTTP::header "Cache-Control"}
    verifyEq "Header X-Forwarded-SSL" "true" {HTTP::header "X-Forwarded-SSL"}

    run rules/2.tcl http
}

@landro what do you think about providing some additional subpackage like ::TesTcl::verify:: for ready to use most common verification procedures (ex. verify::header or verify::statusCode)?

@Sebastian-Brzuzek
Copy link
Contributor

and about error...
in last argument for verify procedure you have to provide code to evaluate for condition checking.
As long as it is provided as {} (list) there is no variable substitution made by TCL interpreter. This is OK for static values. To solve this problem you have to substitute headerName variable name to pass value into verify instead of variable name. Possible solution:

proc verifyHeader {headerName expectedHeaderValue} {
    verify "Header '$headerName' should be '$expectedHeaderValue'" $expectedHeaderValue eq [list HTTP::header $headerName]
}

@landro
Copy link
Owner

landro commented Oct 14, 2013

@Sebastian-Brzuzek I've been thinking about this stuff today. As you said, we should try to keep testcl as tiny as possible. Less code means less code to maintain ... Before we add lots of functionality, we really need to get feedback from our user base (which I believe is quite small ... ). Makes sense?

@Espenhh
Copy link
Author

Espenhh commented Oct 15, 2013

@Sebastian-Brzuzek that solution solved it perfectly! Thanks :)

I agree that it's good to keep the library small at this point. Maybe the documentation could include an example using procedures to show people what's possible, I guess a lot of people who will be using this library are not very proficient in the Tcl language, so a little help in the right direction would be good :)

Feel free to close this issue if you don't want to include any helper-functions at this point.

@Sebastian-Brzuzek
Copy link
Contributor

@Espenhh I think it is great idea to add some more examples to documentation or even better to update existing examples with this kind of procedures to not force people read too many examples/docs.

@landro I fully agree that we should get feedback. Is there some voting mechanism which we can use to find what is "common"? I was using https://www.google.com/moderator/ for this kind of problems, but maybe there is something better. We should agree on some rules like adding only procedures which will collect some minimum number of votes?

BTW, I think we should move this discussion to our mailing list https://groups.google.com/forum/#!forum/testcl-user and close this issue until we will decide which procedures to add and how to organize this. @landro do you agree?

@landro
Copy link
Owner

landro commented Oct 15, 2013

I'll close this for now, and open a discussen on the google group.

2013/10/15 Sebastian Brzuzek notifications@github.com

@Espenhh https://github.com/Espenhh I think it is great idea to add
some more examples to documentation or even better to update existing
examples with this kind of procedures to not force people read too many
examples/docs.

@landro https://github.com/landro I fully agree that we should get
feedback. Is there some voting mechanism which we can use to find what is
"common"? I was using https://www.google.com/moderator/ for this kind of
problems, but maybe there is something better. We should agree on some
rules like adding only procedures which will collect some minimum number of
votes?

BTW, I think we should move this discussion to our mailing list
https://groups.google.com/forum/#!forum/testcl-user and close this issue
until we will decide which procedures to add and how to organize this.
@landro https://github.com/landro do you agree?


Reply to this email directly or view it on GitHubhttps://github.com//issues/23#issuecomment-26319217
.

BEKK Open
http://open.bekk.no

TesTcl - a unit test framework for iRules
http://testcl.com

@landro landro closed this as completed Oct 15, 2013
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants