Skip to content

Commit 493b94b

Browse files
committed
Introduced support for skiptoken operation in query options #118
1 parent 4e2bcbe commit 493b94b

File tree

9 files changed

+99
-47
lines changed

9 files changed

+99
-47
lines changed

examples/SharePoint/view_examples.php

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,8 @@
33
require_once('../bootstrap.php');
44

55
use Office365\PHP\Client\Runtime\Auth\AuthenticationContext;
6+
use Office365\PHP\Client\Runtime\ClientAction;
7+
use Office365\PHP\Client\Runtime\Utilities\RequestOptions;
68
use Office365\PHP\Client\SharePoint\ClientContext;
79

810
global $Settings;
@@ -12,18 +14,15 @@
1214
$authCtx = new AuthenticationContext($Settings['Url']);
1315
$authCtx->acquireTokenForUser($Settings['UserName'],$Settings['Password']);
1416
$ctx = new ClientContext($Settings['Url'],$authCtx);
15-
1617
//$listTitle = "Orders_" . rand(1,1000);
1718
$listTitle = "Tasks" ;
18-
1919
printListViews($ctx,$listTitle);
2020
}
2121
catch (Exception $e) {
2222
echo 'Error: ', $e->getMessage(), "\n";
2323
}
2424

2525

26-
2726
function printListViews(ClientContext $ctx, $listTitle){
2827
$list = $ctx->getWeb()->getLists()->getByTitle($listTitle);
2928
$views = $list->getViews();

src/Runtime/ClientObjectCollection.php

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -230,6 +230,18 @@ public function skip($value)
230230
}
231231

232232

233+
/**
234+
* Sets the number of records to skip before it retrieves records in a collection.
235+
* @param $value
236+
* @return ClientObjectCollection $this
237+
*/
238+
public function skiptoken($value)
239+
{
240+
$this->queryOptions->SkipToken = rawurlencode($value);
241+
return $this;
242+
}
243+
244+
233245
/**
234246
* Creates resource for a collection
235247
* @return ClientObject

src/Runtime/OData/ODataQueryOptions.php

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -42,5 +42,7 @@ private function getProperties(){
4242

4343
public $Skip;
4444

45+
public $SkipToken;
46+
4547
public $Search;
4648
}

src/Runtime/OData/ODataRequest.php

Lines changed: 24 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@
66

77
use Exception;
88
use Office365\PHP\Client\Runtime\ClientAction;
9+
use Office365\PHP\Client\Runtime\ClientObject;
910
use Office365\PHP\Client\Runtime\ClientRequestStatus;
1011
use Office365\PHP\Client\Runtime\ClientResult;
1112
use Office365\PHP\Client\Runtime\IEntityType;
@@ -70,45 +71,44 @@ public function processResponse($response)
7071
$resultObject = $this->resultObjects[$this->getCurrentAction()->getId()];
7172

7273
if ($this->getCurrentAction() instanceof InvokePostMethodQuery && $this->getCurrentAction()->MethodBody instanceof ChangeLogItemQuery) {
73-
$payload = $this->parseXmlResponse($response);
74+
$this->processXmlResponse($response,$resultObject);
7475
} else {
75-
$payload = $this->parseJsonResponse($response);
76-
}
77-
78-
if ($resultObject instanceof ClientResult) {
79-
if ($this->getCurrentAction() instanceof InvokeMethodQuery){
80-
$this->getSerializationContext()->RootElement = $this->getCurrentAction()->MethodName;
81-
}
82-
$resultObject->fromJson($payload,$this->getSerializationContext());
83-
} else if($resultObject instanceof IEntityType) {
84-
$this->getSerializationContext()->map($payload,$resultObject);
85-
$this->getCurrentAction()->getResourcePath()->ServerObjectIsNull = false;
76+
$this->processJsonResponse($response,$resultObject);
8677
}
8778
}
8879

8980

9081
/**
9182
* @param string $response
92-
* @return mixed
83+
* @param ClientObject|ClientResult $resultObject
9384
* @throws Exception
9485
*/
95-
private function parseJsonResponse($response)
86+
private function processJsonResponse($response, $resultObject)
9687
{
97-
$error = array();
88+
$errorPayload = array();
9889
$payload = json_decode($response);
99-
if ($this->validateResponse($payload, $error) == false) {
100-
throw new Exception($error['Message']);
90+
if ($this->validateResponse($payload, $errorPayload) == false) {
91+
throw new Exception($errorPayload['Message']);
92+
}
93+
94+
if ($resultObject instanceof ClientResult) {
95+
if ($this->getCurrentAction() instanceof InvokeMethodQuery){
96+
$this->getSerializationContext()->RootElement = $this->getCurrentAction()->MethodName;
97+
}
98+
$resultObject->fromJson($payload,$this->getSerializationContext());
99+
} else if($resultObject instanceof IEntityType) {
100+
$this->getSerializationContext()->map($payload,$resultObject);
101+
$this->getCurrentAction()->getResourcePath()->ServerObjectIsNull = false;
101102
}
102-
return $payload;
103103
}
104104

105105

106106
/**
107107
* Process Xml response from SharePoint REST service
108108
* @param string $response
109-
* @return array
109+
* @param ClientObject $resultObject
110110
*/
111-
private function parseXmlResponse($response)
111+
private function processXmlResponse($response, $resultObject)
112112
{
113113
$payload = array();
114114
$xml = simplexml_load_string($response);
@@ -122,7 +122,7 @@ private function parseXmlResponse($response)
122122
}
123123
$payload[] = $item;
124124
}
125-
return $payload;
125+
$this->getSerializationContext()->map($payload,$resultObject);
126126
}
127127

128128

@@ -200,6 +200,9 @@ protected function getCurrentAction(){
200200
}
201201

202202

203+
/**
204+
* @return ClientRequest
205+
*/
203206
public function getNextRequest()
204207
{
205208
$request = new ODataRequest($this->context);

src/Runtime/Utilities/RequestOptions.php

Lines changed: 8 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -28,23 +28,12 @@ public function __construct($url, $headers = array(), $data = null, $methodType
2828
$this->Verbose = false;
2929
$this->SSLVersion = null;
3030
$this->StreamHandle = null;
31+
$this->Data = $data;
3132
}
3233

3334
public function toArray()
3435
{
35-
return [
36-
'Url' => $this->Url,
37-
'Method' => $this->Method,
38-
'Headers' => $this->Headers,
39-
'Data' => $this->Data,
40-
'IncludeBody' => $this->IncludeBody,
41-
'IncludeHeaders' => $this->IncludeHeaders,
42-
'AuthType' => $this->AuthType,
43-
'Verbose' => $this->Verbose,
44-
'UserCredentials' => $this->UserCredentials,
45-
'SSLVersion' => $this->SSLVersion,
46-
'StreamHandle' => $this->StreamHandle,
47-
];
36+
return get_object_vars($this);
4837
}
4938

5039
public function addCustomHeader($name, $value)
@@ -136,4 +125,10 @@ function ($k, $v) {
136125
*/
137126
public $StreamHandle;
138127

128+
129+
/**
130+
* @var string
131+
*/
132+
public $Proxy;
133+
139134
}

src/SharePoint/SPList.php

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,6 @@ class SPList extends SecurableObject
2222
*/
2323
public function addItem(array $listItemCreationInformation)
2424
{
25-
2625
$items = new ListItemCollection($this->getContext(),
2726
new ResourcePathEntity($this->getContext(),$this->getResourcePath(),"items"));
2827
$listItem = new ListItem($this->getContext());

tests/ClientContextTests.php renamed to tests/ClientContextTest.php

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,9 @@
11
<?php
22

33

4-
class ClientContextTests extends SharePointTestCase
4+
class ClientContextTest extends SharePointTestCase
55
{
6+
67
public function testIfSingleRequestProcessed()
78
{
89
try{
@@ -34,4 +35,4 @@ public function testIfMultipleRequestsProcessed()
3435
}
3536
}
3637

37-
}
38+
}

tests/ListItemExtensions.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -74,12 +74,12 @@ public static function deleteListItems(\Office365\PHP\Client\SharePoint\SPList $
7474
}
7575

7676

77-
7877
/**
7978
* Create list item operation
8079
* @param \Office365\PHP\Client\SharePoint\SPList $list
8180
* @param array $itemProperties
8281
* @return \Office365\PHP\Client\SharePoint\ListItem
82+
* @throws Exception
8383
*/
8484
public static function createListItem(\Office365\PHP\Client\SharePoint\SPList $list, array $itemProperties){
8585
$ctx = $list->getContext();

tests/ListItemTest.php

Lines changed: 47 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -28,8 +28,6 @@ public static function tearDownAfterClass()
2828
}
2929

3030

31-
32-
3331
public function testItemsCount()
3432
{
3533
$itemsCount = self::$targetList->getProperty("ItemCount");
@@ -46,17 +44,17 @@ public function testCreateListItems()
4644
$currentUser = self::$context->getWeb()->getCurrentUser();
4745
self::$context->load($currentUser);
4846
self::$context->executeQuery();
49-
5047
$itemProperties = array(
5148
'Title' => 'Order Approval' . rand(1, 1000),
5249
'Body' => 'Please review a task',
5350
'AssignedToId' => $currentUser->getProperty("Id"),
5451
'PredecessorsId' => array( 'results' => array($currentUser->getProperty("Id")))
5552
//'__metadata' => array('type' => 'SP.Data.TasksListItem')
5653
);
57-
$item = ListItemExtensions::createListItem(self::$targetList, $itemProperties);
58-
$this->assertEquals($item->getProperty('Body'), $itemProperties['Body']);
59-
return $item;
54+
$items = $this->populateList($itemProperties,1);
55+
$firstItem = $items[0];
56+
$this->assertEquals($firstItem->getProperty('Body'), $itemProperties['Body']);
57+
return $firstItem;
6058
}
6159

6260

@@ -134,6 +132,38 @@ public function testQueryOptionsForMultiUserField()
134132
}
135133

136134

135+
public function testQueryOptionsSkipToken()
136+
{
137+
$minItemsCount = 10;
138+
$maxItemId = null;
139+
$itemsCount = self::$targetList->getProperty("ItemCount");
140+
if ($itemsCount < $minItemsCount) {
141+
$itemProperties = array(
142+
'Title' => 'Order Approval' . rand(1, 1000),
143+
'Body' => 'Please review a task'
144+
);
145+
$this->populateList($itemProperties, $minItemsCount - $itemsCount);
146+
}
147+
148+
$items = self::$targetList->getItems();
149+
self::$context->load($items);
150+
self::$context->executeQuery();
151+
$maxItemId = max(
152+
array_map(function (ListItem $item) {
153+
return $item->getProperty("Id");
154+
}, $items->getData())
155+
);
156+
157+
158+
$items = self::$targetList->getItems()
159+
->top($minItemsCount)
160+
->skiptoken("Paged=TRUE&p_SortBehavior=0&p_ID=" . $maxItemId);
161+
self::$context->load($items);
162+
self::$context->executeQuery();
163+
$this->assertEquals(0, $items->getCount());
164+
}
165+
166+
137167

138168
public function testDeleteListItems()
139169
{
@@ -151,5 +181,16 @@ public function testDeleteListItems()
151181
$this->assertEquals($itemsCount, 0);
152182
}
153183

184+
185+
public function populateList($itemProperties,$itemsCount)
186+
{
187+
$items = [];
188+
$idx = 0;
189+
while($idx < $itemsCount){
190+
$items[] = ListItemExtensions::createListItem(self::$targetList, $itemProperties);
191+
$idx++;
192+
}
193+
return $items;
194+
}
154195

155196
}

0 commit comments

Comments
 (0)