Completed
Pull Request — master (#30)
by
unknown
09:00
created

SiteTreeFullBuildEngine::setUrlArrayObject()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 3
Code Lines 2

Duplication

Lines 0
Ratio 0 %
Metric Value
dl 0
loc 3
rs 10
cc 1
eloc 2
nc 1
nop 1
1
<?php
2
3
/**
4
 * Similar to {@link RebuildStaticPagesTask}, but only queues pages for republication
5
 * in the {@link StaticPagesQueue}. This queue is worked off by an independent task running constantly on the server.
6
 */
7
class SiteTreeFullBuildEngine extends BuildTask {
8
9
	/**
10
	 * @var URLArrayObject
11
	 */
12
	protected $urlArrayObject;
13
14
	private static $dependencies = array(
15
		'urlArrayObject' =>  '%$URLArrayObject'
16
	);
17
18
	/**
19
	 *
20
	 * @var string
21
	 */
22
	protected $description = 'Full cache rebuild: adds all pages on the site to the static publishing queue';
23
24
	/** @var int - chunk size (set via config) */
25
	private static $records_per_request = 200;
26
27
28
	/**
29
	 * Checks if this task is enabled / disabled via the config setting
30
	 */
31
	public function __construct() {
32
		parent::__construct();
33
		if($this->config()->get('disabled') === true) {
34
			$this->enabled = false;
35
		}
36
	}
37
38
	public function setUrlArrayObject($o) {
39
		$this->urlArrayObject = $o;
40
	}
41
42
	public function getUrlArrayObject() {
43
		return $this->urlArrayObject;
44
	}
45
46
	/**
47
	 *
48
	 * @param SS_HTTPRequest $request
49
	 * @return bool
50
	 */
51
	public function run($request) {
52
53
		if($request->getVar('urls') && is_array($request->getVar('urls'))) {
54
			return $this->queueURLs($request->getVar('urls'));
55
		}
56
		if($request->getVar('urls')) {
57
			return $this->queueURLs(explode(',', $request->getVar('urls')));
58
		}
59
60
		// The following shenanigans are necessary because a simple Page::get()
61
		// will run out of memory on large data sets. This will take the pages
62
		// in chunks by running this script multiple times and setting $_GET['start'].
63
		// Chunk size can be set via yml (SiteTreeFullBuildEngine.records_per_request).
64
		// To disable this functionality, just set a large chunk size and pass start=0.
65
		increase_time_limit_to();
66
		$self = get_class($this);
67
		$verbose = isset($_GET['verbose']);
68
69
		if (isset($_GET['start'])) {
70
			$this->runFrom((int)$_GET['start']);
71
		} else {
72
			foreach(array('framework','sapphire') as $dirname) {
73
				$script = sprintf("%s%s$dirname%scli-script.php", BASE_PATH, DIRECTORY_SEPARATOR, DIRECTORY_SEPARATOR);
74
				if (file_exists($script)) break;
75
			}
76
77
			$total = $this->getAllLivePages()->count();
78
			echo "Adding all pages to the queue. Total: $total\n\n";
79
			for ($offset = 0; $offset < $total; $offset += self::config()->records_per_request) {
80
				echo "$offset..";
81
				$cmd = "php $script dev/tasks/$self start=$offset";
82
				if($verbose) echo "\n  Running '$cmd'\n";
83
				$res = $verbose ? passthru($cmd) : `$cmd`;
84
				if($verbose) echo "  ".preg_replace('/\r\n|\n/', '$0  ', $res)."\n";
85
			}
86
		}
87
	}
88
89
90
	/**
91
	 * Process a chunk of pages
92
	 * @param $start
93
	 */
94
	protected function runFrom($start) {
95
		$chunkSize = (int)self::config()->records_per_request;
96
		$pages = $this->getAllLivePages()->sort('ID')->limit($chunkSize, $start);
97
		$count = 0;
98
99
		$arrNonCachedPages = array();
100
101
		// Collect all URLs into the queue
102
		foreach($pages as $page) {
103
104
			if (is_callable(array($page, 'canCache')) && !$page->canCache()) {
105
				$arrNonCachedPages[] =
106
				continue;
0 ignored issues
show
Bug introduced by
This code did not parse for me. Apparently, there is an error somewhere around this line:

Syntax error, unexpected T_CONTINUE
Loading history...
107
			}
108
109
			if (is_callable(array($page, 'urlsToCache'))) {
110
				$this->getUrlArrayObject()->addUrlsOnBehalf($page->urlsToCache(), $page);
111
				$count++;
112
			}
113
		}
114
115
		$publisher = singleton('SiteTree')->getExtensionInstance('FilesystemPublisher');
116
		if ($publisher) {
117
			foreach ($arrNonCachedPages as $page) {
118
				$pathsArray = $publisher->urlsToPaths(array($page->Link()));
119
				$filePath = $publisher->getDestDir() . '/' . array_shift($pathsArray);
120
				@unlink($filePath);
121
				$staleFilepath = str_replace(pathinfo($filePath, PATHINFO_EXTENSION), 'stale.html', $filePath);
122
				@unlink($staleFilepath);
123
			}
124
		}
125
126
		echo sprintf("SiteTreeFullBuildEngine: Queuing %d pages".PHP_EOL, $count);
127
	}
128
129
130
	/**
131
	 * Adds an array of urls to the Queue
132
	 *
133
	 * @param array $urls
134
	 * @return bool - if any pages were queued
135
	 */
136
	protected function queueURLs($urls = array()) {
137
		echo sprintf("SiteTreeFullBuildEngine: Queuing %d pages".PHP_EOL, count($urls));
138
		if(!count($urls)) {
139
			return false;
140
		}
141
		$this->getUrlArrayObject()->addUrls($urls);
142
		return true;
143
	}
144
145
	/**
146
	 *
147
	 * @return DataList
148
	 */
149
	protected function getAllLivePages() {
150
		ini_set('memory_limit', '512M');
151
		$oldMode = Versioned::get_reading_mode();
152
		if(class_exists('Subsite')) {
153
			Subsite::disable_subsite_filter(true);
154
		}
155
		if(class_exists('Translatable')) {
156
			Translatable::disable_locale_filter();
157
		}
158
		Versioned::reading_stage('Live');
159
		$pages = DataObject::get("SiteTree");
160
		Versioned::set_reading_mode($oldMode);
161
		return $pages;
162
	}
163
164
}
165