Project

General

Profile

Plugin system » History » Version 10

Oscar van Eijk, 02/07/2011 03:26 PM

1 10 Oscar van Eijk
{{>toc}}
2
3 1 Oscar van Eijk
h1. Plugin system
4
5 5 Oscar van Eijk
Since VirtueMart v2, the Joomla! plugin system is used form payment and shipper plugins.
6 1 Oscar van Eijk
7
h2. Installing plugins
8
9
During development the the VM2 branch, the plugins are not available as Joomla install packages, so for test environments, they must be installed manually.
10
11
h3. Payment plugins
12
13
At the time of writing, only 2 of the former payment plugins have been converted to the new plugin system. Others should follow soon, all help is appreciated!!
14
15
Use the SQL query below to add the plugins to your database (assuming the table prefix is "jos_"):
16
17
<pre>
18 4 Devendra Kumar Shukla
INSERT INTO `jos_plugins` (`id`, `name`, `element`, `folder`, `access`, `ordering`
19 1 Oscar van Eijk
  , `published`, `iscore`, `client_id`, `checked_out`, `checked_out_time`, `params`)
20
VALUES
21
 (NULL, 'VMPayment - Authorize', 'authorize', 'vmpayment', 0, 0, 1, 0, 0, 0, '0000-00-00 00:00:00', '')
22
,(NULL, 'VMPayment - Cash on delivery', 'cashondel', 'vmpayment', 0, 0, 1, 0, 0, 0, '0000-00-00 00:00:00','')
23
;
24
</pre>
25
26 2 Oscar van Eijk
Next, copy the plugin files (authorize.php, authorize.xml, cashondel.php and cashondel.xml), located in the folder /plugins/vmpayment in the SVN checkout, to the Joomla plugin directory. If that doesn't exist, it must be created first: <pre>mkdir <document_root>/plugins/vmpayment</pre>
27 1 Oscar van Eijk
28
Now, in the store maintenance, you can add payment methods based on one of these plugins. Note at this moment it is required to select a vendor!
29
30
h3. Shipper plugins
31
32
This is very similar to the payment plugins. Only 1 plugin has been created (again: all help is appreciated!); 'standard', which provides a basic shipping option for postal services.
33 3 Oscar van Eijk
*Note:* Installing the sample data does _NOT_ provide shipping rates anymore!
34 1 Oscar van Eijk
35
Use the SQL query below to add the plugins to your database (assuming the table prefix is "jos_"):
36
37
<pre>
38 4 Devendra Kumar Shukla
INSERT INTO `jos_plugins` (`id`, `name`, `element`, `folder`, `access`, `ordering`
39 1 Oscar van Eijk
  , `published`, `iscore`, `client_id`, `checked_out`, `checked_out_time`, `params`)
40
VALUES
41
 (NULL, 'VMShipper - Standard', 'standard', 'vmshipper', 0, 0, 1, 0, 0, 0, '0000-00-00 00:00:00', '')
42
;
43
</pre>
44
45 2 Oscar van Eijk
Next, copy the plugin files (standard.php and standard.xml), located in the folder /plugins/vmshipper in the SVN checkout, to the Joomla plugin directory. If that doesn't exist, it must be created first: <pre>mkdir <document_root>/plugins/vmshipper</pre>
46 1 Oscar van Eijk
47
Now use the 'Shipping' menu item in the backend to add 1 or more carriers based on this plugin. All you need to do here is give the shipper a name and select a vendor (this is optional; when no vendor is selected, this carrier is valid for all vendors).
48
Finally you can add the shipping rates for the created vendor. Make sure a there's always a valid shipping rate: customers select the carrier only and the plugin must be able to find a mathcing rate based on the total order weight and the shipto address!
49
50 5 Oscar van Eijk
h2. Plugin Development
51 1 Oscar van Eijk
52 5 Oscar van Eijk
All plugins for VirtueMart should be developed confirming the Joomla! plugin development methods. Refer to http://docs.joomla.org/Tutorial:Plugins for developers documentation for Joomla! plugins.
53
54
h3. Payment Plugins
55
56 7 Oscar van Eijk
Payment plugins are used both in the front-end and the backend. They must be created as classes deriving from the base class *vmPaymentPlugin*:
57 9 Oscar van Eijk
<pre><code class="php">
58 7 Oscar van Eijk
class plgVmPayment<myPlugin> extends vmPaymentPlugin {
59
	function plgVmPayment<myPlugin>(&$subject, $config) {
60
		$this->_pelement = basename(__FILE__, '.php');	// Required!
61
		$this->_createTable();				// Required, see below
62
		parent::__construct($subject, $config);
63
	}
64
}
65 9 Oscar van Eijk
</code></pre>
66 7 Oscar van Eijk
67
Below is the list with events and a description on what moment they are fired.
68 6 Oscar van Eijk
* *plgVmOnSelectPayment()* - This event is fired during the checkout process. It allows the shopper to select one of the available payment methods.
69 5 Oscar van Eijk
It should display a radio button (name: paym_id) to select the payment method. Other information (like credit card info) might be selected as well, depending on the plugin.
70
+Return:+
71
It must return the HTML code for displaying the form (radio button and optional extra selections).
72
+Parameters:+
73
# (VirtueMartCart object) The cart object 
74
# (integer, default 0) ID of an already selected payment method ID, if any
75
76 6 Oscar van Eijk
* *plgVmOnPaymentSelectCheck()* - This event is fired after the payment method has been selected. It can be used to store
77 5 Oscar van Eijk
additional payment info in the cart.
78
+Return:+
79
Plugins that were not selected must return null, otherwise True of False must be returned indicating Success or Failure.
80
+Parameters:+
81
# (VirtueMartCart object) The cart object 
82
83 10 Oscar van Eijk
84
85 6 Oscar van Eijk
* *plgVmOnCheckoutCheckPaymentData()* - This event is fired during the checkout process. It can be used to validate the payment data as entered by the user.
86 5 Oscar van Eijk
+Return:+
87
Plugins that were not selected must return null, otherwise True of False must be returned indicating Success or Failure.
88
+Parameters:+
89
None
90
91 6 Oscar van Eijk
* *plgVmOnConfirmedOrderStorePaymentData()* - This event is fired after the payment has been processed; it stores the payment method-specific data.
92 5 Oscar van Eijk
All plugins _must_ reimplement this method.
93
+Return:+
94
If the plugin is NOT actually executed (not the selected payment method), this method must return NULL
95
If this plugin IS executed, it MUST return the order status code that the order should get. This triggers the stock updates if required
96
+Parameters:+
97
# (integer) The ordernumber being processed
98
# (object) Data from the cart
99
# (array) Price information for this order
100
	
101 6 Oscar van Eijk
* *plgVmOnShowOrderPaymentBE()* - This method is fired when showing the order details in the backend. It displays the the payment method-specific data.
102 5 Oscar van Eijk
All plugins _must_ reimplement this method.
103
+Return:+
104
Null when for payment methods that were not selected, text (HTML) otherwise
105
+Parameters:+
106
# (integer) The order ID
107
# (integer) Payment method used for this order
108
109 6 Oscar van Eijk
* *plgVmOnCancelPayment()* - This event is fired each time the status of an order is changed to Cancelled. It can be used to refund payments, void authorization etc.
110 5 Oscar van Eijk
When reimplementing this methis, the body _must_ start with this code:
111 9 Oscar van Eijk
<pre><code class="php">$_paymethodID = $this->getPaymentMethodForOrder($_orderID);
112 5 Oscar van Eijk
if (!$this->selectedThisMethod($this->_pelement, $_paymethodID)) {
113
	return;
114 9 Oscar van Eijk
}</code></pre>
115 5 Oscar van Eijk
+Parameters:+
116
 (integer The order ID
117
 (char) Previous order status
118
 (char) New order status
119
120 6 Oscar van Eijk
* *plgVmOnShipOrderPayment()* - This event is fired when the status of an order is changed to Shipped. It can be used to confirm or capture payments
121 5 Oscar van Eijk
When reimplementing this methis, the body _must_ start with this code:
122 9 Oscar van Eijk
<pre><code class="php">$_paymethodID = $this->getPaymentMethodForOrder($_orderID);
123 5 Oscar van Eijk
if (!$this->selectedThisMethod($this->_pelement, $_paymethodID)) {
124
	return;
125 9 Oscar van Eijk
}</code></pre>
126 5 Oscar van Eijk
+Return:+
127
True on success, False on failure, Null if this plugin was not activated
128
+Parameters:+
129 1 Oscar van Eijk
# (integer) Order ID
130 7 Oscar van Eijk
131
Other helper functions inherited from the base class:
132
133 9 Oscar van Eijk
* *_ createTable()* - This method is used to create and maintain the plugin specific database table(s).
134 7 Oscar van Eijk
It _must_ be reimplemented by all plugins.
135 1 Oscar van Eijk
+Example:+
136 8 Oscar van Eijk
<pre><code class="php">
137 7 Oscar van Eijk
$_scheme = DbScheme::get_instance();
138
$_scheme->create_scheme('#__vm_order_payment_'.$this->_pelement);
139
$_schemeCols = array(
140
	 'id' => array (
141
			 'type' => 'int'
142
			,'length' => 11
143
			,'auto_inc' => true
144
			,'null' => false
145
	)
146
	,'order_id' => array (
147
			 'type' => 'int'
148
			,'length' => 11
149
			,'null' => false
150
	)
151
	,'payment_method_id' => array (
152
			 'type' => 'text'
153
			,'null' => false
154
	)
155
);
156
$_schemeIdx = array(
157
	 'idx_order_payment' => array(
158
			 'columns' => array ('order_id')
159
			,'primary' => false
160
			,'unique' => false
161
			,'type' => null
162
	)
163
);
164
$_scheme->define_scheme($_schemeCols);
165
$_scheme->define_index($_schemeIdx);
166
if (!$_scheme->scheme()) {
167
	JError::raiseWarning(500, $_scheme->get_db_error());
168
}
169
$_scheme->reset();
170 8 Oscar van Eijk
</code></pre>
171 7 Oscar van Eijk
172 8 Oscar van Eijk
* *getPaymentMethodForOrder()* - Get the order payment ID for a given order number
173 7 Oscar van Eijk
+Return:+
174
The payment method ID, or -1 when not found 
175
+Parameters:+
176
# (integer) The order ID
177
178 8 Oscar van Eijk
* *getThisMethodName()* - Get the name of the payment method.
179 7 Oscar van Eijk
This method can _not_ be reimplemented
180
+Return:+
181
Paymenent method name
182
+Parameters:+
183
# (integer) The payment method ID
184
185 8 Oscar van Eijk
* *selectedThisMethod()* - This method checks if the selected payment method matches the current plugin
186 7 Oscar van Eijk
+Return:+
187
True if the calling plugin has the given payment ID, False otherwise.
188
+Parameters:+
189
# (string) Element name, taken from the plugin filename
190
# (integer) The payment method ID
191
192 8 Oscar van Eijk
* *writePaymentData()* - This method writes all payment plugin specific data to the plugin's table
193 7 Oscar van Eijk
+Return:+
194
True if the calling plugin has the given payment ID, False otherwise.
195
+Parameters:+
196
# (array) Indexed array in the format 'column_name' => 'value'
197
# (string) Table name
198 10 Oscar van Eijk
199
h3. Shipper Plugins
200
201
Shipper plugins are used both in the front-end and the backend. They must be created as classes deriving from the base class *vmShipperPlugin*:
202
<pre><code class="php">
203
class plgVmShipper<myPlugin> extends vmShipperPlugin {
204
	function plgVmPayment<myPlugin>(&$subject, $config) {
205
		$this->_pelement = basename(__FILE__, '.php');	// Required!
206
		$this->_createTable();				// Required, see below
207
		parent::__construct($subject, $config);
208
	}
209
}
210
</code></pre>
211
212
Here's a short overview of the events:
213
* When a shopper selects a shipper, *plgOnSelectShipper()* is fired. It displays the shipper and can be used for collecting extra - shipper specific - info.
214
* After selecting, *plgVmShipperSelected()* can be used to store extra shipper info in the cart. The selected shipper ID will be stored in the cart by the checkout process before this method is fired.
215
* *plgOnConfirmShipper()* is fired when the order is confirmed and stored to the database. It is called before the rest of the order or stored, when reimplemented, it _must_ include a call to parent::plgOnConfirmShipper() (or execute the same steps to put all data in the cart)
216
217
When a stored order is displayed in the backend, the following events are used:
218
* *plgVmOnShowOrderShipperBE()* displays specific data about (a) shipment(s) (NOTE: this plugin is _OUTSIDE_ any form!)
219
* *plgVmOnShowOrderLineShipperBE()*) can be used to show information about a single orderline, e.g. display a package code at line level when more packages are shipped.
220
* *plgVmOnEditOrderLineShipperBE() can be used add a package code for an order line when more packages are shipped.
221
* *plgVmOnUpdateOrderShipperBE()* is fired inside a form. It can be used to add shipper data, like package code.
222
* *plgVmOnSaveOrderShipperBE()* is fired from the backend after the order has been saved. If one of the show methods above have to option to add or edit info, this method must be used to save the data.
223
* *plgVmOnUpdateOrderLine()* is fired from the backend after an order line has been saved. This method must be reimplemented if plgVmOnEditOrderLineShipperBE() is used.
224
225
The frontend 1 show method:
226
* plgVmOnShowOrderShipperFE() collects and displays specific data about (a) shipment(s)
227
228
Below is the list with events and a description on what moment they are fired.
229
230
* *plgVmOnSelectShipper()* - This event is fired during the checkout process. It allows the shopper to select one of the available shippers.
231
It should display a radio button (name: shipper_id) to select the shipper. In the description, the shipping cost can also be displayed, based on the total order weight and the shipto country (this wil be calculated again during order confirmation)
232
+Return:+
233
HTML code to display the form
234
+Parameters:+
235
# (VirtueMartCart object)  Cart object
236
# (integer, default 0) ID of the currently shipper selected
237
238
* *plgVmOnShipperSelected()* - This event is fired after the shipping method has been selected. It can be used to store additional shipper info in the cart.
239
+Return:+
240
True on succes, false on failures, null when this plugin was not selected.
241
On errors, JError::raiseWarning (or JError::raiseError) must be used to set a message.
242
+Parameters:+
243
# (VirtueMartCart object)  Cart object
244
# (integer, default 0) ID of the shipper selected
245
246
* *plgVmOnConfirmShipper()* - This event is fired after the payment has been processed; it selects the actual shipping rate based on the shipto (country, zip) and/or order weight, and optionally writes extra info to the database (in which case this method must be reimplemented).
247
Reimplementation is not required, but when done, the following check MUST be made:
248
<pre><code class="php">
249
if (!$this->selectedThisShipper($this->_selement, $_cart->shipper_id)) {
250
	return null;
251
}</code></pre>
252
+Return:+
253
The shipping rate ID
254
Do _not_ return parent::plgVmOnConfirmShipper($_cart); it is valid but will produce extra overhead!
255
+Parameters:+
256
# (VirtueMartCart object) Cart object
257
258
* *plgVmOnShowOrderShipperBE()* - This method is fired when showing the order details in the backend. It displays the shipper-specific data.
259
NOTE, this plugin should NOT be used to display form fields, since it's called outside a form! Use *plgVmOnUpdateOrderBE()( instead!
260
+Return:+
261
Null for shippers that aren't active, text (HTML) otherwise
262
+Parameters:+
263
# (integer) The order ID
264
# (integer) Vendor ID
265
# (object) Object with 2 properties 'carrier' and 'name' 
266
267
* *plgVmOnEditOrderLineShipperBE()* - This method is fired when editing the order line details in the backend. It can be used to add line specific package codes
268
+Return:+
269
Null for shippers that aren't active, text (HTML) otherwise
270
+Parameters:+
271
# (integer) The order ID
272
# (integer) The order Line ID
273
274
* *plgVmOnUpdateOrderShipper()* - Save updated order data to the shipper specific table
275
+Return:+
276
True on success, false on failures (the rest of the save-process will be skipped!), or null when this shipper is not actived.
277
+Parameters:+
278
# (array) Form data
279
280
* *plgVmOnUpdateOrderLineShipper()* - Save updated orderline data to the shipper specific table
281
+Return:+
282
True on success, false on failures (the rest of the save-process will be skipped!), or null when this shipper is not actived.
283
+Parameters:+
284
# (array) Form data
285
286
* *plgVmOnShowOrderShipperFE()* - This method is fired when showing the order details in the frontend.  It displays the shipper-specific data.
287
+Return:+
288
Null for shippers that aren't active, text (HTML) otherwise
289
+Parameters:+
290
# (integer) The order ID
291
292
* *plgVmOnShowOrderLineShipperFE()* - This method is fired when showing the order details in the frontend, for every orderline. It can be used to display line specific package codes, e.g. with a link to external tracking and tracing systems
293
+Return:+
294
Null for shippers that aren't active, text (HTML) otherwise
295
+Parameters:+
296
# (integer) The order ID
297
# (integer) The order LineID
298
299
Other helper functions inherited from the base class:
300
301
* *_ createTable()* - This method is used to create and maintain the plugin specific database table(s).
302
It _must_ be reimplemented by all plugins.
303
+Example:+
304
<pre><code class="php">$_scheme = DbScheme::get_instance();
305
$_scheme->create_scheme('#__vm_order_shipper_'.$this->_selement);
306
$_schemeCols = array(
307
	 'id' => array (
308
			 'type' => 'int'
309
			,'length' => 11
310
			,'auto_inc' => true
311
			,'null' => false
312
	)
313
	,'order_id' => array (
314
			 'type' => 'int'
315
			,'length' => 11
316
			,'null' => false
317
	)
318
	,'shipper_id' => array (
319
			 'type' => 'text'
320
			,'null' => false
321
	)
322
);
323
$_schemeIdx = array(
324
	 'idx_order_payment' => array(
325
			 'columns' => array ('order_id')
326
			,'primary' => false
327
			,'unique' => false
328
			,'type' => null
329
	)
330
);
331
$_scheme->define_scheme($_schemeCols);
332
$_scheme->define_index($_schemeIdx);
333
if (!$_scheme->scheme()) {
334
	JError::raiseWarning(500, $_scheme->get_db_error());
335
}
336
$_scheme->reset();
337
</code></pre>
338
339
* *getThisShipperName()* -  Get the name of the shipper
340
+Return:+
341
Shipper name
342
+Parameters:+
343
# (integer) The Shipper ID
344
	final protected function ($_sid)
345
346
* *writeShipperData()* - This method writes all shipper plugin specific data to the plugin's table
347
+Parameters:+
348
# (array) Indexed array in the format 'column_name' => 'value'
349
# (string) Table name
350
351
* *getShippingRateIDForOrder()* - Get the shipping rate ID for a given order number
352
+Return:+
353
The shipping rate ID, or -1 when not found 
354
+Parameters:+
355
# (integer) The order ID
356
357
* *getShippingRate()* -  Get the total price for a shipping rate
358
+Return:+
359
Price in display format
360
+Parameters:+
361
# (integer) Shipping rate ID
362
	
363
* *getShipperIDForOrder()* - Get the shipper ID for a given order number
364
+Return:+
365
The shipper ID, or -1 when not found 
366
+Parameters:+
367
# (integer) The order ID
368
369
* *selectShippingRate()* - Select the shipping rate ID, based on the selected shipper in combination with the shipto address (country and zipcode) and the total order weight.
370
+Return:+
371
Shipping rate ID, -1 when no match is found. Only 1 selected ID will be returned; if more ID's match, the cheapest will be selected.
372
+Parameters:+
373
# (VirtueMartCart object) Cart object
374
# (integer, default 0) Shipper ID, by default taken from the cart
375
376
* *selectedThisShipper()* - This method checks if the selected shipper matches the current plugin
377
+Return:+
378
True if the calling plugin has the given payment ID
379
+Parameters:+
380
# (string) Element name, taken from the plugin filename
381
# (integer) The shipper ID
382
383
* *getOrderWeight()* - Get the total weight for the order, based on which the proper shipping rate can be selected.
384
+Return:+
385
Total weight for the order
386
+Parameters:+
387
# (VirtueMartCart object) Cart object
388
389
* *getShipToCountry()* - Translate the country ID to the country code as used in the shipper configuration.
390
+Return:+
391
3 character country code
392
+Parameters:+
393
# (VirtueMartCart object) Cart object
394
395
* *getShipToZipcode()* - Get the shipto zip from the cart
396
+Return:+
397
Zipcode
398
+Parameters:+
399
# (VirtueMartCart object) Cart object
400
401
* *getCarriers()* - Fill an array with all carriers found with this plugin for the current vendor
402
+Return:+
403
True when carrier(s) was (were) found for this vendor, false otherwise
404
+Parameters:+
405
# (integer) The vendor ID taken from the cart.
406
407
* *validateVendor()* - Check if this shipper has carriers for the current vendor.
408
+Return:+
409
True when a shipper_id was found for this vendor, false otherwise
410
+Parameters:+
411
# (integer) The vendor ID taken from the cart.