Exemple #1
0
    def __init__(self, context):
        """
        Base request for OData/REST service

        :type context: office365.runtime.client_runtime_context.ClientRuntimeContext
        """
        self.context = context
        self._queries = []
        self.beforeExecute = EventHandler()
        self.afterExecute = EventHandler()
    def __init__(self, context):
        """
        Abstract request client

        :type context: office365.runtime.client_runtime_context.ClientRuntimeContext
        """
        self._context = context
        self._queries = []
        self._current_query = None
        self.beforeExecute = EventHandler()
        self.afterExecute = EventHandler()
    def __init__(self, context, item_type, resource_path=None):
        """Client object collection

        :type context: office365.runtime.client_runtime_context.ClientRuntimeContext
        :type item_type: type[ClientObject]
        :type resource_path: office365.runtime.resource_path.ResourcePath
        """
        super(ClientObjectCollection, self).__init__(context, resource_path)
        self._data = []
        self._item_type = item_type
        self.page_loaded = EventHandler(False)
        self._default_page_size = 100
        self._paged_mode = True
        self._page_index = 0
        self.next_request_url = None
class ClientRequest(object):

    def __init__(self, context):
        """
        Base request for OData/REST service

        :type context: office365.runtime.client_runtime_context.ClientRuntimeContext
        """
        self._context = context
        self._queries = []
        self._current_query = None
        self.beforeExecute = EventHandler()
        self.afterExecute = EventHandler()

    @property
    def context(self):
        return self._context

    @property
    def current_query(self):
        """
        :rtype: office365.runtime.queries.client_query.ClientQuery
        """
        return self._current_query

    @property
    def queries(self):
        """
        :rtype: list[ClientQuery]
        """
        return self._queries

    def add_query(self, query, to_begin=False):
        """
        :type to_begin: bool
        :type query: office365.runtime.queries.client_query.ClientQuery
        """
        if to_begin:
            self._queries.insert(0, query)
        else:
            self._queries.append(query)
        self._current_query = query

    def remove_query(self, query):
        self._queries.remove(query)
        self._current_query = None

    @abstractmethod
    def build_request(self):
        """
        :rtype: office365.runtime.http.request_options.RequestOptions
        """
        pass

    @abstractmethod
    def process_response(self, response):
        """
        :type response: requests.Response
        """
        pass

    def execute_query(self):
        """Submit a pending request to the server"""
        for _ in self.next_query():
            try:
                request = self.build_request()
                self.beforeExecute.notify(request)
                response = self.execute_request_direct(request)
                response.raise_for_status()
                self.process_response(response)
                self.afterExecute.notify(response)
            except HTTPError as e:
                raise ClientRequestException(*e.args, response=e.response)

    def execute_request_direct(self, request_options):
        """Execute client request

        :type request_options: office365.runtime.http.request_options.RequestOptions
        """
        self.context.authenticate_request(request_options)
        if request_options.method == HttpMethod.Post:
            if request_options.is_bytes or request_options.is_file:
                result = requests.post(url=request_options.url,
                                       headers=request_options.headers,
                                       data=request_options.data,
                                       auth=request_options.auth,
                                       verify=request_options.verify)
            else:
                result = requests.post(url=request_options.url,
                                       headers=request_options.headers,
                                       json=request_options.data,
                                       auth=request_options.auth,
                                       verify=request_options.verify)
        elif request_options.method == HttpMethod.Patch:
            result = requests.patch(url=request_options.url,
                                    headers=request_options.headers,
                                    json=request_options.data,
                                    auth=request_options.auth,
                                    verify=request_options.verify)
        elif request_options.method == HttpMethod.Delete:
            result = requests.delete(url=request_options.url,
                                     headers=request_options.headers,
                                     auth=request_options.auth,
                                     verify=request_options.verify)
        elif request_options.method == HttpMethod.Put:
            result = requests.put(url=request_options.url,
                                  data=request_options.data,
                                  headers=request_options.headers,
                                  auth=request_options.auth,
                                  verify=request_options.verify)
        else:
            result = requests.get(url=request_options.url,
                                  headers=request_options.headers,
                                  auth=request_options.auth,
                                  verify=request_options.verify,
                                  stream=request_options.stream,
                                  proxies=request_options.proxies)
        return result

    def next_query(self):
        while len(self._queries) > 0:
            qry = self._queries.pop(0)
            self._current_query = qry
            yield qry
class ClientObjectCollection(ClientObject):
    def __init__(self, context, item_type, resource_path=None):
        """Client object collection

        :type context: office365.runtime.client_runtime_context.ClientRuntimeContext
        :type item_type: type[ClientObject]
        :type resource_path: office365.runtime.resource_path.ResourcePath
        """
        super(ClientObjectCollection, self).__init__(context, resource_path)
        self._data = []
        self._item_type = item_type
        self.page_loaded = EventHandler(False)
        self._default_page_size = 100
        self._paged_mode = True
        self._page_index = 0
        self.next_request_url = None

    def get(self):
        """
        :rtype: ClientObjectCollection
        """
        return super(ClientObjectCollection, self).get()

    def clear(self):
        self._data = []

    def create_typed_object(self, properties):
        if self._item_type is None:
            raise AttributeError("No class for object type '{0}' found".format(
                self._item_type))

        client_object = self._item_type(self.context)
        client_object._parent_collection = self
        for k, v in properties.items():
            client_object.set_property(k, v, False)
        return client_object

    def set_property(self, name, value, persist_changes=False):
        child_client_object = self.create_typed_object(value)
        self.add_child(child_client_object)

    def add_child(self, client_object):
        """
        Adds client object into collection

        :type client_object: ClientObject
        """
        client_object._parent_collection = self
        self._data.append(client_object)

    def remove_child(self, client_object):
        self._data.remove(client_object)

    def __iter__(self):
        """
        :rtype: collections.Iterable[ClientObject]
        """
        for cur_item in self._data:
            yield cur_item

        if self._paged_mode:
            while self.next_request_url:
                for cur_item in self._get_next_items():
                    yield cur_item

    def __len__(self):
        return len(self._data)

    def __getitem__(self, index):
        """

        :type index: int
        :rtype: ClientObject
        """
        item_iterator = iter(self)
        while len(self._data) <= index:
            next(item_iterator)
        return self._data[index]

    def filter(self, expression):
        """
        Sets OData $filter query option

        :type expression: str
        """
        self.query_options.filter = expression
        return self

    def order_by(self, value):
        """
        Sets OData $orderBy query option

        :type value: int
        """
        self.query_options.orderBy = value
        return self

    def skip(self, value):
        """
        Sets $skip system query option

        :type value: int
        """
        self.query_options.skip = value
        return self

    def top(self, value):
        """
        :type value: int
        """
        self._paged_mode = False
        self.query_options.top = value
        return self

    def get_items_count(self):
        """
        Gets total items count
        :return: ClientResult
        """
        result = ClientResult(None)

        def _calc_items_count(resp):
            list(iter(self))
            result.value = len(self)

        self.context.load(self)
        self.context.after_execute(_calc_items_count)
        return result

    def _load_paged_items(self):
        request = RequestOptions(self.next_request_url)
        response = self.context.execute_request_direct(request)
        json = response.json()
        self.next_request_url = None
        self.context.pending_request().map_json(json, self)

    def _get_next_items(self):
        self._page_index += 1
        next_index = self._default_page_size * self._page_index
        self._load_paged_items()
        self.page_loaded.notify(len(self._data))
        return self._data[next_index:]
Exemple #6
0
class ClientRequest(object):
    def __init__(self, context):
        """
        Base request for OData/REST service

        :type context: office365.runtime.client_runtime_context.ClientRuntimeContext
        """
        self.context = context
        self._queries = []
        self.beforeExecute = EventHandler()
        self.afterExecute = EventHandler()

    def __iter__(self):
        while self._queries:
            qry = self._queries.pop(0)
            yield qry

    def __len__(self):
        return len(self._queries)

    def __getitem__(self, index):
        return self._queries[index]

    @property
    def queries(self):
        """
        :rtype: list[ClientQuery]
        """
        return self._queries

    def add_query(self, query):
        """
        :type query: ClientQuery
        """
        self._queries.append(query)

    @abstractmethod
    def build_request(self):
        pass

    @abstractmethod
    def process_response(self, response):
        pass

    def execute_query(self):
        """Submit a pending request to the server"""
        try:
            request = self.build_request()
            self.beforeExecute.notify(request)
            response = self.execute_request_direct(request)
            response.raise_for_status()
            self.process_response(response)
            self.afterExecute.notify(response)
        except HTTPError as e:
            raise ClientRequestException(*e.args, response=e.response)

    def execute_request_direct(self, request_options):
        """Execute client request

        :type request_options: RequestOptions
        """
        self.context.authenticate_request(request_options)
        if request_options.method == HttpMethod.Post:
            if request_options.is_bytes or request_options.is_file:
                result = requests.post(url=request_options.url,
                                       headers=request_options.headers,
                                       data=request_options.data,
                                       auth=request_options.auth,
                                       verify=request_options.verify)
            else:
                result = requests.post(url=request_options.url,
                                       headers=request_options.headers,
                                       json=request_options.data,
                                       auth=request_options.auth,
                                       verify=request_options.verify)
        elif request_options.method == HttpMethod.Patch:
            result = requests.patch(url=request_options.url,
                                    headers=request_options.headers,
                                    json=request_options.data,
                                    auth=request_options.auth,
                                    verify=request_options.verify)
        elif request_options.method == HttpMethod.Delete:
            result = requests.delete(url=request_options.url,
                                     headers=request_options.headers,
                                     auth=request_options.auth,
                                     verify=request_options.verify)
        elif request_options.method == HttpMethod.Put:
            result = requests.put(url=request_options.url,
                                  data=request_options.data,
                                  headers=request_options.headers,
                                  auth=request_options.auth,
                                  verify=request_options.verify)
        else:
            result = requests.get(url=request_options.url,
                                  headers=request_options.headers,
                                  auth=request_options.auth,
                                  verify=request_options.verify,
                                  stream=request_options.stream,
                                  proxies=request_options.proxies)
        return result
class ClientObjectCollection(ClientObject):
    def __init__(self, context, child_item_type, resource_path=None):
        """Client object collection

        :type context: office365.runtime.client_runtime_context.ClientRuntimeContext
        :type child_item_type: type[ClientObject]
        :type resource_path: office365.runtime.client_path.ClientPath
        """
        super(ClientObjectCollection, self).__init__(context, resource_path)
        self._data = []
        self._item_type = child_item_type
        self.page_loaded = EventHandler(False)
        self._page_size = 100
        self._paged_mode = True
        self._page_index = 0
        self.next_request_url = None

    @property
    def entity_type_name(self):
        name = super(ClientObjectCollection, self).entity_type_name
        return "Collection({0})".format(name)

    def get(self):
        """
        :rtype: ClientObjectCollection
        """
        return super(ClientObjectCollection, self).get()

    def clear(self):
        self._data = []

    def create_typed_object(self, properties=None, persist_changes=False):
        """
        :type properties: dict
        :type persist_changes: bool
        :rtype: ClientObject
        """
        if properties is None:
            properties = {}
        if self._item_type is None:
            raise AttributeError("No class for entity type '{0}' found".format(
                self._item_type))

        client_object = self._item_type(self.context)
        client_object._parent_collection = self
        for k, v in properties.items():
            client_object.set_property(k, v, persist_changes)
        return client_object

    def set_property(self, name, value, persist_changes=False):
        """
        :type name: str
        :type value: any
        :type persist_changes: bool
        """
        child_client_object = self.create_typed_object(value)
        self.add_child(child_client_object)
        return self

    def add_child(self, client_object):
        """
        Adds client object into collection

        :type client_object: ClientObject
        """
        client_object._parent_collection = self
        self._data.append(client_object)
        return self

    def remove_child(self, client_object):
        """
        :type client_object: ClientObject
        """
        self._data = [item for item in self._data if item != client_object]
        return self

    def __iter__(self):
        """
        :rtype: collections.Iterable[ClientObject]
        """
        for item in self._data:
            yield item

        if self._paged_mode:
            while self.next_request_url:
                paged_items = self._load_next_items()
                for item in paged_items:
                    yield item

    def __len__(self):
        return len(self._data)

    def __getitem__(self, index):
        """

        :type index: int
        :rtype: ClientObject
        """
        while len(self._data) <= index:
            next(iter(self))
        return self._data[index]

    def to_json(self, json_format=None):
        return [item.to_json(json_format) for item in self._data]

    def filter(self, expression):
        """
        Sets OData $filter query option

        :type expression: str
        """
        self.query_options.filter = expression
        return self

    def order_by(self, value):
        """
        Sets OData $orderBy query option

        :type value: int
        """
        self.query_options.orderBy = value
        return self

    def skip(self, value):
        """
        Sets $skip system query option

        :type value: int
        """
        self.query_options.skip = value
        return self

    def top(self, value):
        """
        :type value: int
        """
        self._page_size = value
        self.query_options.top = value
        return self

    def paged(self, value):
        """
        Enables/disables server-driven paging

        :param int value: bool: sets flag to enable/disable server-driven paging
        """
        self._paged_mode = value
        return self

    def loaded(self, page_loaded=None):
        if callable(page_loaded):
            self.page_loaded += page_loaded

    def get_items_count(self):
        """
        Gets total items count

        :return: ClientResult
        """
        result = ClientResult(self.context)

        def _calc_items_count(resp):
            list(iter(self))
            result.value = len(self)

        self.context.load(self)
        self.context.after_execute(_calc_items_count)
        return result

    def _load_next_items(self):
        request = RequestOptions(self.next_request_url)
        response = self.context.execute_request_direct(request)
        response.raise_for_status()
        self.next_request_url = None
        self.context.pending_request().map_json(response.json(), self)
        self.page_loaded.notify(len(self._data))
        self._page_index += 1
        return self._data[self._page_size * self._page_index:]