Esempio n. 1
0
def session_setup(session, path, index=0):
    _keys = session.keys()
    for key in _keys:
        if key.startswith("_"):
            continue
        elif key in [
                "tests", "graph", "flow_names", "response_type", "test_info",
                "profiles"
        ]:  # don't touch !
            continue
        else:
            del session[key]

    ots = OIDCTestSetup(CONF, TEST_FLOWS, str(CONF.PORT))
    session["testid"] = path
    session["node"] = in_tree(session["graph"], path)
    sequence_info = ots.make_sequence(path)
    sequence_info = ots.add_init(sequence_info)
    session["seq_info"] = sequence_info
    trace = Trace()
    client_conf = ots.config.CLIENT
    conv = Conversation(ots.client, client_conf, trace, None, message_factory,
                        check_factory)
    conv.cache = CACHE
    session["ots"] = ots
    session["conv"] = conv
    session["index"] = index
    session["response_type"] = ""

    return conv, sequence_info, ots, trace, index
Esempio n. 2
0
 def client_init(self):
     ots = OIDCTestSetup(self.conf, self.test_flows, str(self.conf.PORT))
     client_conf = ots.config.CLIENT
     trace = Trace()
     conv = Conversation(ots.client, client_conf, trace, None,
                         message_factory, self.check_factory)
     conv.cache = self.cache
     conv.check_factory = self.check_factory
     return ots, conv
Esempio n. 3
0
 def client_init(self):
     ots = OIDCTestSetup(CONF, TEST_FLOWS.FLOWS, str(CONF.PORT), UmaClient)
     client_conf = ots.config.CLIENT
     trace = Trace()
     conv = Conversation(ots.client, client_conf, trace, None,
                         uma_message_factory, check_factory)
     conv.cache = self.cache
     conv.check_factory = self.check_factory
     return ots, conv
Esempio n. 4
0
    def __init__(self, operations_mod, client_class, msg_factory, chk_factory,
                 conversation_cls):
        self.operations_mod = operations_mod
        self.client_class = client_class
        self.client = None
        self.trace = Trace()
        self.msg_factory = msg_factory
        self.chk_factory = chk_factory
        self.conversation_cls = conversation_cls

        self._parser = argparse.ArgumentParser()
        #self._parser.add_argument('-v', dest='verbose', action='store_true')
        self._parser.add_argument('-d', dest='debug', action='store_true',
                                  help="Print debug information")
        self._parser.add_argument('-v', dest='verbose', action='store_true',
                                  help="Print runtime information")
        self._parser.add_argument(
            '-C', dest="ca_certs",
            help=("CA certs to use to verify HTTPS server certificates,",
                  "if HTTPS is used and no server CA certs are defined then",
                  " no cert verification is done"))
        self._parser.add_argument('-J', dest="json_config_file",
                                  help="Script configuration")
        self._parser.add_argument(
            '-I', dest="interactions",
            help=("Extra interactions not defined in the script ",
                  "configuration file"))
        self._parser.add_argument(
            "-l", dest="list", action="store_true",
            help="List all the test flows as a JSON object")
        self._parser.add_argument(
            "-H", dest="host",
            help=("Which host the script is running on, used to construct the ",
                  "key export URL"))
        self._parser.add_argument(
            "-x", dest="not_verify_ssl", action="store_true",
            help="Don't verify SSL certificates")
        self._parser.add_argument("flow", nargs="?",
                                  help="Which test flow to run")

        self.args = None
        self.pinfo = None
        self.sequences = []
        self.function_args = {}
        self.signing_key = None
        self.encryption_key = None
        self.test_log = []
        self.environ = {}
        self._pop = None
Esempio n. 5
0
def test(environ, session, path):
    _test = path[5:]
    session["flow_index"] = FLOW_SEQUENCE.index(_test)
    session["phase_index"] = 0
    session["start"] = 0
    session["trace"] = Trace()
    _op = resp = client = link = None
    try:
        query = parse_qs(environ["QUERY_STRING"])
    except KeyError:
        pass
    else:
        try:
            session["op"] = query["op"][0]
            try:
                assert session["op"] in SERVER_ENV["OP"]
                _op = session["op_conf"] = SERVER_ENV["OP"][session["op"]]
            except AssertionError:
                return BadRequest("OP chosen that is not configured")
        except KeyError:
            pass
    if _op:
        try:
            client = SERVER_ENV["OIC_CLIENT"][session["opkey"]]
        except KeyError:
            _key = rndstr()
            try:
                kwargs = {"deviate": _op["deviate"]}
            except KeyError:
                kwargs = {}
            client = create_client(_key, **kwargs)
            session["opkey"] = _key
            SERVER_ENV["OIC_CLIENT"][session["opkey"]] = client

        if _op["features"]["discovery"]:
            link = _op["provider"]["dynamic"]
            session["srv_discovery_url"] = link
        else:
            client.handle_provider_config(_op["provider"], session["op"])
    else:
        resp = Redirect("/")

    if resp:
        return resp
    else:
        return {"client": client, "link": link}
Esempio n. 6
0
def test_do_response_400_empty():
    response = Response()
    response.status_code = 400
    response.text = "test"
    response.content = ""

    url = "https://exaample.com/registration"
    client = Client()
    response_type = RegistrationResponse
    trace = Trace()
    state = ""
    kwargs = {}

    resp = do_response(response, CONV, url, trace, client, "json",
                       response_type, state, **kwargs)

    assert resp is None
Esempio n. 7
0
class OAuth2(object):
    client_args = ["client_id", "redirect_uris", "password", "client_secret"]

    def __init__(self, operations_mod, client_class, msg_factory, chk_factory,
                 conversation_cls):
        self.operations_mod = operations_mod
        self.client_class = client_class
        self.client = None
        self.trace = Trace()
        self.msg_factory = msg_factory
        self.chk_factory = chk_factory
        self.conversation_cls = conversation_cls

        self._parser = argparse.ArgumentParser()
        #self._parser.add_argument('-v', dest='verbose', action='store_true')
        self._parser.add_argument('-d', dest='debug', action='store_true',
                                  help="Print debug information")
        self._parser.add_argument('-v', dest='verbose', action='store_true',
                                  help="Print runtime information")
        self._parser.add_argument(
            '-C', dest="ca_certs",
            help=("CA certs to use to verify HTTPS server certificates,",
                  "if HTTPS is used and no server CA certs are defined then",
                  " no cert verification is done"))
        self._parser.add_argument('-J', dest="json_config_file",
                                  help="Script configuration")
        self._parser.add_argument(
            '-I', dest="interactions",
            help=("Extra interactions not defined in the script ",
                  "configuration file"))
        self._parser.add_argument(
            "-l", dest="list", action="store_true",
            help="List all the test flows as a JSON object")
        self._parser.add_argument(
            "-H", dest="host",
            help=("Which host the script is running on, used to construct the ",
                  "key export URL"))
        self._parser.add_argument(
            "-x", dest="not_verify_ssl", action="store_true",
            help="Don't verify SSL certificates")
        self._parser.add_argument("flow", nargs="?",
                                  help="Which test flow to run")

        self.args = None
        self.pinfo = None
        self.sequences = []
        self.function_args = {}
        self.signing_key = None
        self.encryption_key = None
        self.test_log = []
        self.environ = {}
        self._pop = None

    def parse_args(self):
        self.json_config = self.json_config_file()

        try:
            self.features = self.json_config["features"]
        except KeyError:
            self.features = {}

        self.pinfo = self.provider_info()

        self.client_conf(self.client_args)

    def json_config_file(self):
        if self.args.json_config_file == "-":
            return json.loads(sys.stdin.read())
        else:
            return json.loads(open(self.args.json_config_file).read())

    def provider_info(self):
        # Should provide a Metadata class
        res = {}
        _jc = self.json_config["provider"]

        # Backward compatible
        if "endpoints" in _jc:
            try:
                for endp, url in _jc["endpoints"].items():
                    res[endp] = url
            except KeyError:
                pass

        return res

    def test_summation(self, sid):
        status = 0
        for item in self.test_log:
            if item["status"] > status:
                status = item["status"]

        if status == 0:
            status = 1

        info = {
            "id": sid,
            "status": status,
            "tests": self.test_log
        }

        if status == 5:
            for log in reversed(self.test_log):
                if log["status"] == 5:
                    info["url"] = log["url"]
                    info["htmlbody"] = log["message"]
                    break

        return info

    def run(self):
        self.args = self._parser.parse_args()

        if self.args.list:
            return self.operations()
        else:
            if not self.args.flow:
                raise Exception("Missing flow specification")
            self.args.flow = self.args.flow.strip("'")
            self.args.flow = self.args.flow.strip('"')

            flow_spec = self.operations_mod.FLOWS[self.args.flow]
            try:
                block = flow_spec["block"]
            except KeyError:
                block = {}

            self.parse_args()
            _spec = self.make_sequence()
            interact = self.get_interactions()

            try:
                self.do_features(interact, _spec["sequence"], block)
            except Exception, exc:
                exception_trace("do_features", exc)
                return

            #tests = self.get_test()
            self.client.state = "STATE0"

            try:
                expect_exception = flow_spec["expect_exception"]
            except KeyError:
                expect_exception = False

            conv = None
            try:
                if self.pinfo:
                    self.client.provider_info = self.pinfo
                if self.args.verbose:
                    print >> sys.stderr, "Set up done, running sequence"

                args = {}
                for arg in ["extra_args", "kwargs_mod"]:
                    try:
                        args[arg] = self.json_config[arg]
                    except KeyError:
                        args[arg] = {}

                self.trace.info(
                    "client preferences: %s" % self.client.client_prefs)

                conv = self.conversation_cls(self.client, self.cconf,
                                             self.trace, interact,
                                             msg_factory=self.msg_factory,
                                             check_factory=self.chk_factory,
                                             expect_exception=expect_exception,
                                             **args)
                try:
                    conv.ignore_check = self.json_config["ignore_check"]
                except KeyError:
                    pass

                conv.do_sequence(_spec)
                #testres, trace = do_sequence(oper,
                self.test_log = conv.test_output
                tsum = self.test_summation(self.args.flow)
                if tsum["status"] > 1 or self.args.debug:
                    print >> sys.stdout, json.dumps(tsum)
                    print >> sys.stderr, self.trace
            except (FatalError, UnSupported), err:
                self.test_log = conv.test_output
                tsum = self.test_summation(self.args.flow)
                print >> sys.stdout, json.dumps(tsum)
                print >> sys.stderr, self.trace
                # try:
                #     print >> sys.stderr, err.trace
                # except AttributeError:
                #     pass
                # print err
                #exception_trace("RUN", err)
            except PyoidcError, err:
                if err.message:
                    self.trace.info("Protocol message: %s" % err.message)
                print >> sys.stderr, self.trace
                print err
                exception_trace("RUN", err)
Esempio n. 8
0
def application(environ, start_response):
    """
    :param environ: The HTTP application environment
    :param start_response: The application to run when the handling of the
        request is done
    :return: The response as a list of lines
    """
    global OAS
    session = environ['beaker.session']
    path = environ.get('PATH_INFO', '').lstrip('/')
    response_encoder = ResponseEncoder(environ=environ,
                                       start_response=start_response)
    parameters = parse_qs(environ["QUERY_STRING"])

    if path == "robots.txt":
        return static(environ, start_response, "static/robots.txt")

    if path.startswith("static/"):
        return static(environ, start_response, path)
    elif path.startswith("log"):
        return display_log(environ, start_response)
    elif path.startswith("_static/"):
        return static(environ, start_response, path)
    
    trace = Trace()

    if path == "test_list":
        return rp_test_list(environ, start_response)
    elif path == "":
        return registration(environ, start_response)
    elif path == "generate_client_credentials":
        client_id, client_secret = generate_static_client_credentials(parameters)
        return response_encoder.return_json(
            json.dumps({"client_id": client_id,
                        "client_secret": client_secret}))
    elif path == "claim":
        _oas = session["op"]
        authz = environ["HTTP_AUTHORIZATION"]
        try:
            assert authz.startswith("Bearer")
        except AssertionError:
            resp = BadRequest()
        else:
            tok = authz[7:]
            try:
                _claims = _oas.claim_access_token[tok]
            except KeyError:
                resp = BadRequest()
            else:
                del _oas.claim_access_token[tok]
                resp = Response(json.dumps(_claims), content='application/json')
        return resp(environ, start_response)

    mode, endpoint = extract_mode(path)

    if endpoint == ".well-known/webfinger":
        _p = urlparse(parameters["resource"][0])
        if _p.scheme in ["http", "https"]:
            mode = {"test_id": _p.path[1:]}
        elif _p.scheme == "acct":
            _l, _ = _p.path.split('@')
            mode = {"test_id": _l}
        else:
            resp = ServiceError("Unknown scheme: {}".format(_p.scheme))
            return resp(environ, start_response)

    if mode:
        session["test_id"] = mode["test_id"]

    if "op" not in session:
        session["op"] = setup_op(mode, COM_ARGS, OP_ARG)
        session["mode_path"] = mode2path(mode)
    else:  # may be a new mode
        _path = mode2path(mode)
        if session["mode_path"] != _path:
            session["op"] = setup_op(mode, COM_ARGS, OP_ARG)
            session["mode_path"] = _path

    for regex, callback in URLS:
        match = re.search(regex, endpoint)
        if match is not None:
            trace.request("PATH: %s" % endpoint)
            trace.request("METHOD: %s" % environ["REQUEST_METHOD"])
            try:
                trace.request(
                    "HTTP_AUTHORIZATION: %s" % environ["HTTP_AUTHORIZATION"])
            except KeyError:
                pass

            try:
                environ['oic.url_args'] = match.groups()[0]
            except IndexError:
                environ['oic.url_args'] = endpoint

            LOGGER.info("callback: %s" % callback)
            try:
                if hasattr(callback, 'func'):
                    return callback.func(environ, start_response, session, trace)
                else:
                    return callback(environ, start_response, session, trace)
            except Exception as err:
                print >> sys.stderr, "%s" % err
                message = traceback.format_exception(*sys.exc_info())
                print >> sys.stderr, message
                LOGGER.exception("%s" % err)
                resp = ServiceError("%s" % err)
                return resp(environ, start_response)

    LOGGER.debug("unknown side: %s" % endpoint)
    resp = NotFound("Couldn't find the side you asked for!")
    return resp(environ, start_response)
Esempio n. 9
0
    def __init__(self, operations_mod, client_class, msg_factory, chk_factory,
                 conversation_cls):
        self.operations_mod = operations_mod
        self.client_class = client_class
        self.client = None
        self.trace = Trace()
        self.msg_factory = msg_factory
        self.chk_factory = chk_factory
        self.conversation_cls = conversation_cls

        self._parser = argparse.ArgumentParser()
        #self._parser.add_argument('-v', dest='verbose', action='store_true')
        self._parser.add_argument('-d', dest='debug', action='store_true',
                                  help="Print debug information")
        self._parser.add_argument('-v', dest='verbose', action='store_true',
                                  help="Print runtime information")
        self._parser.add_argument(
            '-C', dest="ca_certs",
            help="CA certs to use to verify HTTPS server certificates,"
                 "if HTTPS is used and no server CA certs are defined then"
                 " no cert verification is done")
        self._parser.add_argument('-J', dest="json_config_file",
                                  help="Script configuration")
        self._parser.add_argument(
            '-I', dest="interactions",
            help="Extra interactions not defined in the script "
                 "configuration file")
        self._parser.add_argument(
            "-l", dest="list", action="store_true",
            help="List all the test flows as a JSON object")
        self._parser.add_argument(
            "-H", dest="host",
            help="Which host the script is running on, used to construct the "
                 "key export URL")
        self._parser.add_argument(
            "-x", dest="not_verify_ssl", action="store_true",
            help="Don't verify SSL certificates")
        self._parser.add_argument(
            '-B', dest="bailout",
            help="When user interaction is needed but not supported: break and"
                 "dump state to file")
        self._parser.add_argument(
            '-Ki', dest="cookie_imp",
            help="File from which to import authentication/authz cookies"
        )
        self._parser.add_argument(
            '-Ke', dest="cookie_exp",
            help="File to export authentication/authz cookies to"
        )
        self._parser.add_argument(
            '-R', dest="restart",
            help="Restart test flow, resetting state to what's in the file")
        self._parser.add_argument("flow", nargs="?",
                                  help="Which test flow to run")

        self.args = None
        self.pinfo = None
        self.sequences = []
        self.function_args = {}
        self.signing_key = None
        self.encryption_key = None
        self.test_log = []
        self.environ = {}
        self._pop = None
        self.json_config = None
        self.features = {}
Esempio n. 10
0
from rrtest import Trace
from oictest.oprp import not_supported
from oictest.base import Conversation
from oictest.check import factory as check_factory
from oictest.oidcrp import Client
from oic.oic.message import factory as message_factory

__author__ = 'roland'

_cli = Client()
CONV = Conversation(_cli, {}, Trace(), None,
                    message_factory, check_factory=check_factory)


def test_not_support():
    assert not_supported("abc", "abc") is None
    assert not_supported("bac", "abc") == ["bac"]
    assert not_supported("abc", ["abc", "def"]) is None
    assert not_supported("bac", ["abc", "def"]) == ["bac"]
    assert not_supported(["abc", "def"], ["abc", "def"]) is None
    assert not_supported(["bac", "def"], ["abc", "def"]) == ["bac"]
    assert not_supported(["abc", "def", "ghi"], ["abc", "def"]) == ["ghi"]

# TODO pi.google does not exist
# def test_support():
#     pi = json.loads(open("pi.google").read())
#     CONV.client.provider_info = ProviderConfigurationResponse(**pi)
#
#     stat = support(CONV, {'warning': {
#         'scopes_supported': ['profile', 'email', 'address', 'phone']}})
#
Esempio n. 11
0
    try:
        client = resp["client"]
        link = resp["link"]
    except (KeyError, TypeError):
        client = link = None

    try:
        flow = FLOWS[FLOW_SEQUENCE[session["flow_index"]]]
        if session["start"]:
            request = False
        else:
            request = True
    except (KeyError, TypeError):
        session["flow_index"] = 0
        session["phase_index"] = 0
        session["trace"] = Trace()
        request = True
        flow = FLOWS[FLOW_SEQUENCE[session["flow_index"]]]

    _phase = PHASES[flow["sequence"][session["phase_index"]]]

    _trace = session["trace"]
    if _trace is None:
        _trace = session["trace"] = Trace()
    _cli = None
    if not request:  # Do response first
        if client:
            _cli = client
        else:
            _cli = SERVER_ENV["OIC_CLIENT"][session["opkey"]]
Esempio n. 12
0
    import importlib
    from oictest.base import Conversation
    from oictest.check import factory as check_factory
    from oictest.oidcrp import Client
    from oic.oic.message import factory as message_factory

    parser = argparse.ArgumentParser()
    parser.add_argument('-l', dest='log')
    parser.add_argument('-d', dest='dir')
    parser.add_argument('-c', dest="config")
    parser.add_argument('-D', dest="rec")
    args = parser.parse_args()

    if args.config:
        sys.path.insert(0, ".")
        CONF = importlib.import_module(args.config)
        conv = Conversation(Client, CONF.CLIENT, Trace(), None,
                            message_factory, check_factory=check_factory)

    if args.log:
        headers, trace, test, test_result = do_file(args.log)
        print headers["Timestamp"], test_result[0]

    if args.dir:
        print do_dir(args.dir)

    if args.rec:
        mat = {}
        res = do_dir(args.rec)
        print json.dumps(res)
Esempio n. 13
0
    def __init__(self, operations_mod, combo, msg_factory, chk_factory,
                 conversation_cls):
        self.operations_mod = operations_mod

        self.uma = combo
        self.roles = combo.keys()
        self.entity = {}
        self.cconf = {}
        self.pinfo = {}

        self.trace = Trace()
        self.msg_factory = msg_factory
        self.chk_factory = chk_factory
        self.conversation_cls = conversation_cls

        self._parser = argparse.ArgumentParser()
        #self._parser.add_argument('-v', dest='verbose', action='store_true')
        self._parser.add_argument('-d',
                                  dest='debug',
                                  action='store_true',
                                  help="Print debug information")
        self._parser.add_argument('-v',
                                  dest='verbose',
                                  action='store_true',
                                  help="Print runtime information")
        self._parser.add_argument(
            '-C',
            dest="ca_certs",
            help=("CA certs to use to verify HTTPS server certificates,",
                  "if HTTPS is used and no server CA certs are defined then",
                  " no cert verification is done"))
        self._parser.add_argument('-J',
                                  dest="json_config_file",
                                  help="Script configuration")
        self._parser.add_argument(
            '-I',
            dest="interactions",
            help=("Extra interactions not defined in the script ",
                  "configuration file"))
        self._parser.add_argument(
            "-l",
            dest="list",
            action="store_true",
            help="List all the test flows as a JSON object")
        self._parser.add_argument(
            "-H",
            dest="host",
            help=(
                "Which host the script is running on, used to construct the ",
                "key export URL"))
        self._parser.add_argument("-x",
                                  dest="not_verify_ssl",
                                  action="store_true",
                                  help="Don't verify SSL certificates")
        self._parser.add_argument("flow",
                                  nargs="?",
                                  help="Which test flow to run")
        self._parser.add_argument(
            '-e',
            dest="external_server",
            action='store_true',
            help="A external web server are used to handle key export")

        self.args = None
        self.sequences = []
        self.function_args = {}
        self.signing_key = None
        self.encryption_key = None
        self.test_log = []
        self.environ = {}
        self._pop = None
        self.json_config = None
        self.features = {}
        self.keysrv_running = False
Esempio n. 14
0
    def __init__(self, operations_mod, client_class, msg_factory, chk_factory,
                 conversation_cls):
        self.operations_mod = operations_mod
        self.client_class = client_class
        self.client = None
        self.trace = Trace()
        self.msg_factory = msg_factory
        self.chk_factory = chk_factory
        self.conversation_cls = conversation_cls

        self._parser = argparse.ArgumentParser()
        #self._parser.add_argument('-v', dest='verbose', action='store_true')
        self._parser.add_argument('-d',
                                  dest='debug',
                                  action='store_true',
                                  help="Print debug information")
        self._parser.add_argument('-v',
                                  dest='verbose',
                                  action='store_true',
                                  help="Print runtime information")
        self._parser.add_argument(
            '-C',
            dest="ca_certs",
            help="CA certs to use to verify HTTPS server certificates,"
            "if HTTPS is used and no server CA certs are defined then"
            " no cert verification is done")
        self._parser.add_argument('-J',
                                  dest="json_config_file",
                                  help="Script configuration")
        self._parser.add_argument(
            '-I',
            dest="interactions",
            help="Extra interactions not defined in the script "
            "configuration file")
        self._parser.add_argument(
            "-l",
            dest="list",
            action="store_true",
            help="List all the test flows as a JSON object")
        self._parser.add_argument(
            "-H",
            dest="host",
            help="Which host the script is running on, used to construct the "
            "key export URL")
        self._parser.add_argument("-x",
                                  dest="not_verify_ssl",
                                  action="store_true",
                                  help="Don't verify SSL certificates")
        self._parser.add_argument(
            '-B',
            dest="bailout",
            help="When user interaction is needed but not supported: break and"
            "dump state to file")
        self._parser.add_argument(
            '-Ki',
            dest="cookie_imp",
            help="File from which to import authentication/authz cookies")
        self._parser.add_argument(
            '-Ke',
            dest="cookie_exp",
            help="File to export authentication/authz cookies to")
        self._parser.add_argument(
            '-R',
            dest="restart",
            help="Restart test flow, resetting state to what's in the file")
        self._parser.add_argument("flow",
                                  nargs="?",
                                  help="Which test flow to run")

        self.args = None
        self.pinfo = None
        self.sequences = []
        self.function_args = {}
        self.signing_key = None
        self.encryption_key = None
        self.test_log = []
        self.environ = {}
        self._pop = None
        self.json_config = None
        self.features = {}
Esempio n. 15
0
class OAuth2(object):
    client_args = ["client_id", "redirect_uris", "password", "client_secret"]

    def __init__(self, operations_mod, client_class, msg_factory, chk_factory,
                 conversation_cls):
        self.operations_mod = operations_mod
        self.client_class = client_class
        self.client = None
        self.trace = Trace()
        self.msg_factory = msg_factory
        self.chk_factory = chk_factory
        self.conversation_cls = conversation_cls

        self._parser = argparse.ArgumentParser()
        #self._parser.add_argument('-v', dest='verbose', action='store_true')
        self._parser.add_argument('-d',
                                  dest='debug',
                                  action='store_true',
                                  help="Print debug information")
        self._parser.add_argument('-v',
                                  dest='verbose',
                                  action='store_true',
                                  help="Print runtime information")
        self._parser.add_argument(
            '-C',
            dest="ca_certs",
            help="CA certs to use to verify HTTPS server certificates,"
            "if HTTPS is used and no server CA certs are defined then"
            " no cert verification is done")
        self._parser.add_argument('-J',
                                  dest="json_config_file",
                                  help="Script configuration")
        self._parser.add_argument(
            '-I',
            dest="interactions",
            help="Extra interactions not defined in the script "
            "configuration file")
        self._parser.add_argument(
            "-l",
            dest="list",
            action="store_true",
            help="List all the test flows as a JSON object")
        self._parser.add_argument(
            "-H",
            dest="host",
            help="Which host the script is running on, used to construct the "
            "key export URL")
        self._parser.add_argument("-x",
                                  dest="not_verify_ssl",
                                  action="store_true",
                                  help="Don't verify SSL certificates")
        self._parser.add_argument(
            '-B',
            dest="bailout",
            help="When user interaction is needed but not supported: break and"
            "dump state to file")
        self._parser.add_argument(
            '-Ki',
            dest="cookie_imp",
            help="File from which to import authentication/authz cookies")
        self._parser.add_argument(
            '-Ke',
            dest="cookie_exp",
            help="File to export authentication/authz cookies to")
        self._parser.add_argument(
            '-R',
            dest="restart",
            help="Restart test flow, resetting state to what's in the file")
        self._parser.add_argument("flow",
                                  nargs="?",
                                  help="Which test flow to run")

        self.args = None
        self.pinfo = None
        self.sequences = []
        self.function_args = {}
        self.signing_key = None
        self.encryption_key = None
        self.test_log = []
        self.environ = {}
        self._pop = None
        self.json_config = None
        self.features = {}

    def parse_args(self):
        self.json_config = self.json_config_file()

        try:
            self.features = self.json_config["features"]
        except KeyError:
            pass

        self.pinfo = self.provider_info()

        self.client_conf(self.client_args)

    def json_config_file(self):
        if self.args.json_config_file == "-":
            return json.loads(sys.stdin.read())
        else:
            return json.loads(open(self.args.json_config_file).read())

    def provider_info(self):
        # Should provide a Metadata class
        res = {}
        _jc = self.json_config["provider"]

        # Backward compatible
        if "endpoints" in _jc:
            try:
                for endp, url in _jc["endpoints"].items():
                    res[endp] = url
            except KeyError:
                pass

        return res

    def test_summation(self, sid):
        status = 0
        for item in self.test_log:
            if item["status"] > status:
                status = item["status"]

        if status == 0:
            status = 1

        info = {"id": sid, "status": status, "tests": self.test_log}

        if status == 5:
            for log in reversed(self.test_log):
                if log["status"] == 5:
                    info["url"] = log["url"]
                    info["htmlbody"] = log["message"]
                    break

        return info

    def run(self):
        self.args = self._parser.parse_args()

        if self.args.list:
            return self.operations()
        else:
            if not self.args.flow:
                raise Exception("Missing flow specification")
            self.args.flow = self.args.flow.strip("'")
            self.args.flow = self.args.flow.strip('"')

            flow_spec = self.operations_mod.FLOWS[self.args.flow]
            try:
                block = flow_spec["block"]
            except KeyError:
                block = {}

            self.parse_args()
            _spec = self.make_sequence()
            _spec["flow"] = flow_spec["sequence"]
            interact = self.get_interactions()

            try:
                self.do_features(interact, _spec, block)
            except Exception, exc:
                exception_trace("do_features", exc)
                return

            try:
                expect_exception = flow_spec["expect_exception"]
            except KeyError:
                expect_exception = False

            conv = None
            try:
                if self.pinfo:
                    self.client.provider_info = self.pinfo
                if self.args.verbose:
                    print >> sys.stderr, "Set up done, running sequence"

                args = {"break": self.args.bailout}
                for arg in ["cookie_imp", "cookie_exp"]:
                    try:
                        val = getattr(self.args, arg)
                    except AttributeError:
                        continue
                    else:
                        args[arg] = val

                cf = self.get_login_cookies()
                if cf:
                    args["login_cookies"] = cf

                for arg in ["extra_args", "kwargs_mod"]:
                    try:
                        args[arg] = self.json_config[arg]
                    except KeyError:
                        args[arg] = {}

                self.trace.info("client preferences: %s" %
                                self.client.client_prefs)

                conv = self.conversation_cls(self.client,
                                             self.cconf,
                                             self.trace,
                                             interact,
                                             msg_factory=self.msg_factory,
                                             check_factory=self.chk_factory,
                                             expect_exception=expect_exception,
                                             **args)
                try:
                    conv.ignore_check = self.json_config["ignore_check"]
                except KeyError:
                    pass

                if self.args.restart:
                    conv.restore_state(self.args.restart)

                conv.do_sequence(_spec)
                #testres, trace = do_sequence(oper,
                self.test_log = conv.test_output
                tsum = self.test_summation(self.args.flow)
                if tsum["status"] > 1 or self.args.debug:
                    print >> sys.stdout, json.dumps(tsum)
                    print >> sys.stderr, self.trace
            except (FatalError, UnSupported), err:
                self.test_log = conv.test_output
                tsum = self.test_summation(self.args.flow)
                print >> sys.stdout, json.dumps(tsum)
                print >> sys.stderr, self.trace
                # try:
                #     print >> sys.stderr, err.trace
                # except AttributeError:
                #     pass
                # print err
                #exception_trace("RUN", err)
            except PyoidcError, err:
                if err.message:
                    self.trace.info("Protocol message: %s" % err.message)
                print >> sys.stderr, self.trace
                print err
                exception_trace("RUN", err)
Esempio n. 16
0
def application(environ, start_response):
    """
    :param environ: The HTTP application environment
    :param start_response: The application to run when the handling of the
        request is done
    :return: The response as a list of lines
    """
    global OAS
    session = environ['beaker.session']
    path = environ.get('PATH_INFO', '').lstrip('/')
    response_encoder = ResponseEncoder(environ=environ,
                                       start_response=start_response)
    parameters = parse_qs(environ["QUERY_STRING"])

    if path == "robots.txt":
        return static(environ, start_response, "static/robots.txt")

    if path.startswith("static/"):
        return static(environ, start_response, path)
    elif path.startswith("log"):
        return display_log(environ, start_response)
    elif path.startswith("_static/"):
        return static(environ, start_response, path)
    
    trace = Trace()

    if path == "test_list":
        return rp_test_list(environ, start_response)
    elif path == "":
        return registration(environ, start_response)
    elif path == "generate_client_credentials":
        client_id, client_secret = generate_static_client_credentials(parameters)
        return response_encoder.return_json(
            json.dumps({"client_id": client_id,
                        "client_secret": client_secret}))
    elif path == "claim":
        _oas = session["op"]
        authz = environ["HTTP_AUTHORIZATION"]
        try:
            assert authz.startswith("Bearer")
        except AssertionError:
            resp = BadRequest()
        else:
            tok = authz[7:]
            try:
                _claims = _oas.claim_access_token[tok]
            except KeyError:
                resp = BadRequest()
            else:
                del _oas.claim_access_token[tok]
                resp = Response(json.dumps(_claims), content='application/json')
        return resp(environ, start_response)

    mode, endpoint = extract_mode(path)

    if endpoint == ".well-known/webfinger":
        _p = urlparse(parameters["resource"][0])
        if _p.scheme in ["http", "https"]:
            mode = {"test_id": _p.path[1:]}
        elif _p.scheme == "acct":
            _l, _ = _p.path.split('@')
            mode = {"test_id": _l}
        else:
            resp = ServiceError("Unknown scheme: {}".format(_p.scheme))
            return resp(environ, start_response)

    if mode:
        session["test_id"] = mode["test_id"]

    if "op" not in session:
        session["op"] = setup_op(mode, COM_ARGS, OP_ARG)
        session["mode_path"] = mode2path(mode)
    else:  # may be a new mode
        _path = mode2path(mode)
        if session["mode_path"] != _path:
            session["op"] = setup_op(mode, COM_ARGS, OP_ARG)
            session["mode_path"] = _path

    for regex, callback in URLS:
        match = re.search(regex, endpoint)
        if match is not None:
            trace.request("PATH: %s" % endpoint)
            trace.request("METHOD: %s" % environ["REQUEST_METHOD"])
            try:
                trace.request(
                    "HTTP_AUTHORIZATION: %s" % environ["HTTP_AUTHORIZATION"])
            except KeyError:
                pass

            try:
                environ['oic.url_args'] = match.groups()[0]
            except IndexError:
                environ['oic.url_args'] = endpoint

            LOGGER.info("callback: %s" % callback)
            try:
                return callback(environ, start_response, session, trace)
            except Exception as err:
                print >> sys.stderr, "%s" % err
                message = traceback.format_exception(*sys.exc_info())
                print >> sys.stderr, message
                LOGGER.exception("%s" % err)
                resp = ServiceError("%s" % err)
                return resp(environ, start_response)

    LOGGER.debug("unknown side: %s" % endpoint)
    resp = NotFound("Couldn't find the side you asked for!")
    return resp(environ, start_response)