Blame view

sources/apps/contacts/js/addressbooks.js 23.3 KB
d1bafeea1   Kload   [fix] Upgrade to ...
1
2
3
4
5
6
7
8
9
10
11
  OC.Contacts = OC.Contacts || {};
  
  
  (function(window, $, OC) {
  	'use strict';
  
  	var AddressBook = function(storage, book, template, isFileAction) {
  		this.isFileAction = isFileAction || false;
  		this.storage = storage;
  		this.book = book;
  		this.$template = template;
6d9380f96   Cédric Dupont   Update sources OC...
12
  	};
d1bafeea1   Kload   [fix] Upgrade to ...
13
14
15
  
  	AddressBook.prototype.render = function() {
  		var self = this;
6d9380f96   Cédric Dupont   Update sources OC...
16
17
  		//var dialog = OC.Contacts.Dialog(null, null);
  		
d1bafeea1   Kload   [fix] Upgrade to ...
18
19
20
21
22
23
  		this.$li = this.$template.octemplate({
  			id: this.book.id,
  			displayname: this.book.displayname,
  			backend: this.book.backend,
  			permissions: this.book.permissions
  		});
6d9380f96   Cédric Dupont   Update sources OC...
24
  		if (this.isFileAction) {
d1bafeea1   Kload   [fix] Upgrade to ...
25
26
27
  			return this.$li;
  		}
  		this.$li.find('a.action').tipsy({gravity: 'w'});
6d9380f96   Cédric Dupont   Update sources OC...
28
  		if (!this.hasPermission(OC.PERMISSION_DELETE)) {
d1bafeea1   Kload   [fix] Upgrade to ...
29
30
  			this.$li.find('a.action.delete').hide();
  		}
6d9380f96   Cédric Dupont   Update sources OC...
31
  		if (!this.hasPermission(OC.PERMISSION_UPDATE)) {
d1bafeea1   Kload   [fix] Upgrade to ...
32
33
  			this.$li.find('a.action.edit').hide();
  		}
6d9380f96   Cédric Dupont   Update sources OC...
34
35
36
37
38
39
  		if (!this.hasPermission(OC.PERMISSION_SHARE)) {
  			this.$li.find('a.action.share').hide();
  		}
  		if (['local', 'ldap'].indexOf(this.getBackend()) === -1) {
  			this.$li.find('a.action.carddav').hide();
  		}
d1bafeea1   Kload   [fix] Upgrade to ...
40
41
42
43
44
45
46
47
48
49
50
51
  		this.$li.find('input:checkbox').prop('checked', this.book.active).on('change', function() {
  			console.log('activate', self.getId());
  			var checkbox = $(this).get(0);
  			self.setActive(checkbox.checked, function(response) {
  				if(!response.error) {
  					self.book.active = checkbox.checked;
  				} else {
  					checkbox.checked = !checkbox.checked;
  				}
  			});
  		});
  		this.$li.find('a.action.download')
6d9380f96   Cédric Dupont   Update sources OC...
52
53
  			.attr('href', OC.generateUrl(
  				'apps/contacts/addressbook/{backend}/{addressBookId}/export',
d1bafeea1   Kload   [fix] Upgrade to ...
54
55
56
57
58
59
60
61
62
63
  				{
  					backend: this.getBackend(),
  					addressBookId: this.getId()
  				}
  			));
  		this.$li.find('a.action.delete').on('click keypress', function() {
  			$('.tipsy').remove();
  			console.log('delete', self.getId());
  			self.destroy();
  		});
6d9380f96   Cédric Dupont   Update sources OC...
64
  		this.$li.find('a.action.carddav').on('click keypress', function() {
d1bafeea1   Kload   [fix] Upgrade to ...
65
66
67
68
69
70
71
72
73
74
75
76
  			var uri = (self.book.owner === oc_current_user ) ? self.book.uri : self.book.uri + '_shared_by_' + self.book.owner;
  			var link = OC.linkToRemote('carddav')+'/addressbooks/'+encodeURIComponent(oc_current_user)+'/'+encodeURIComponent(uri);
  			var $dropdown = $('<li><div id="dropdown" class="drop"><input type="text" value="{link}" readonly /></div></li>')
  				.octemplate({link:link}).insertAfter(self.$li);
  			var $input = $dropdown.find('input');
  			$input.focus().get(0).select();
  			$input.on('blur', function() {
  				$dropdown.hide('blind', function() {
  					$dropdown.remove();
  				});
  			});
  		});
6d9380f96   Cédric Dupont   Update sources OC...
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
  		$('#add-ldap-address-book-element').on('click keypress', function() {
  			var $rightContent = $('#app-content');
  			$rightContent.append('<div id="addressbook-ui-dialog"></div>');
  			var $dlg = $('#addressBookConfigTemplate').octemplate({backend: 'ldap'});
  			var $divDlg = $('#addressbook-ui-dialog');
  			$divDlg.html($dlg).ocdialog({
  				modal: true,
  				closeOnEscape: true,
  				title: t('contacts', 'Add new LDAP Addressbook'),
  				height: 'auto',
  				width: 'auto',
  				buttons: [
  					{
  						text: t('contacts', 'Ok'),
  						click: function() {
  							OC.Contacts.otherBackendConfig.addressbookUiOk($divDlg);
  						},
  						defaultButton: true
  					},
  					{
  						text: t('contacts', 'Cancel'),
  						click: function() {
  							OC.Contacts.otherBackendConfig.addressbookUiClose($divDlg);
d1bafeea1   Kload   [fix] Upgrade to ...
100
  						}
6d9380f96   Cédric Dupont   Update sources OC...
101
102
103
104
  					}
  				],
  				close: function(/*event, ui*/) {
  					OC.Contacts.otherBackendConfig.addressbookUiClose($divDlg);
d1bafeea1   Kload   [fix] Upgrade to ...
105
  				},
6d9380f96   Cédric Dupont   Update sources OC...
106
107
  				open: function(/*event, ui*/) {
  					OC.Contacts.otherBackendConfig.openAddressbookUi();
d1bafeea1   Kload   [fix] Upgrade to ...
108
109
  				}
  			});
6d9380f96   Cédric Dupont   Update sources OC...
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
  		});
  		this.$li.find('a.action.edit').on('click keypress', function(event) {
  			$.when(self.storage.getAddressBook(self.getBackend(), self.getId()))
  			.then(function(response) {
  			if(!response.error) {
  				if(response.data) {
  					var addressbook = response.data;
  					console.log('addressbook', addressbook);
  					if (addressbook.backend === 'local') {
  						if($(this).data('open')) {
  							return;
  						}
  						var editor = this;
  						event.stopPropagation();
  						event.preventDefault();
  						var $dropdown = $('<li><div><input type="text" value="{name}" /></div></li>')
  							.octemplate({name:self.getDisplayName()}).insertAfter(self.$li);
  						var $input = $dropdown.find('input');
  						//$input.focus().get(0).select();
  						$input.addnew({
  							autoOpen: true,
  							//autoClose: false,
  							addText: t('contacts', 'Save'),
  							ok: function(event, name) {
  								console.log('edit-address-book ok', name);
  								$input.addClass('loading');
  								self.update({displayname:name}, function(response) {
  									console.log('response', response);
  									if(response.error) {
  										$(document).trigger('status.contacts.error', response);
  									} else {
  										self.setDisplayName(response.data.displayname);
  										$input.addnew('close');
  									}
  									$input.removeClass('loading');
  								});
  							},
  							close: function() {
  								$dropdown.remove();
  								$(editor).data('open', false);
  							}
  						});
  						$(this).data('open', true);
  					} else {
  						var $rightContent = $('#app-content');
  						$rightContent.append('<div id="addressbook-ui-dialog"></div>');
  						var $dlg = $('#addressBookConfigTemplate').octemplate({backend: 'ldap'});
  						var $divDlg = $('#addressbook-ui-dialog');
  						//var $divDlg = $('#addressbook-ui-dialog');
  						$divDlg.html($dlg).ocdialog({
  							modal: true,
  							closeOnEscape: true,
  							title: t('contacts', 'Edit Addressbook'),
  							height: 'auto', width: 'auto',
  							buttons: [
  								{
  									text: t('contacts', 'Ok'),
  									click: function() {
  										OC.Contacts.otherBackendConfig.addressbookUiEditOk($divDlg);
  										self.setDisplayName($('#addressbooks-ui-name').val());
  									},
  									defaultButton: true
  								},
  								{
  									text: t('contacts', 'Cancel'),
  									click: function() {
  										OC.Contacts.otherBackendConfig.addressbookUiClose($divDlg);
  									}
  								}
  							],
  							close: function() {
  								OC.Contacts.otherBackendConfig.addressbookUiClose($divDlg);
  							},
  							open: function() {
  								OC.Contacts.otherBackendConfig.editAddressbookUI(addressbook);
  							}
  						});
  					}
  					return this.$li;
  				}
  			} else {
  				console.warn('Addressbook getAddressbook - no data !!');
  			}
  			})
  			.fail(function(response) {
  				console.warn('Request Failed:', response.message);
  				$(document).trigger('status.contacts.error', response);
  			});
d1bafeea1   Kload   [fix] Upgrade to ...
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
  		});
  		return this.$li;
  	};
  
  	AddressBook.prototype.getId = function() {
  		return String(this.book.id);
  	};
  
  	AddressBook.prototype.getBackend = function() {
  		return this.book.backend;
  	};
  
  	AddressBook.prototype.getDisplayName = function() {
  		return this.book.displayname;
  	};
  
  	AddressBook.prototype.setDisplayName = function(name) {
  		this.book.displayname = name;
  		this.$li.find('label').text(escapeHTML(name));
  	};
  
  	AddressBook.prototype.getPermissions = function() {
  		return this.book.permissions;
  	};
  
  	AddressBook.prototype.hasPermission = function(permission) {
  		return (this.getPermissions() & permission);
  	};
  
  	AddressBook.prototype.getOwner = function() {
  		return this.book.owner;
  	};
  
  	AddressBook.prototype.getMetaData = function() {
  		return {
  			permissions:this.getPermissions,
  			backend: this.getBackend(),
  			id: this.getId(),
  			displayname: this.getDisplayName()
  		};
  	};
  
  	/**
  	 * Update address book in data store
  	 * @param object properties An object current only supporting the property 'displayname'
  	 * @param cb Optional callback function which
  	 * @return An object with a boolean variable 'error'.
  	 */
  	AddressBook.prototype.update = function(properties, cb) {
  		return $.when(this.storage.updateAddressBook(this.getBackend(), this.getId(), {properties:properties}))
  			.then(function(response) {
  			if(response.error) {
  				$(document).trigger('status.contacts.error', response);
  			}
  			cb(response);
  		});
  	};
  
  	AddressBook.prototype.isActive = function() {
  		return this.book.active;
  	};
  
  	/**
  	 * Save an address books active state to data store.
  	 * @param bool state
  	 * @param cb Optional callback function which
  	 * @return An object with a boolean variable 'error'.
  	 */
  	AddressBook.prototype.setActive = function(state, cb) {
  		var self = this;
  		return $.when(this.storage.activateAddressBook(this.getBackend(), this.getId(), state))
  			.then(function(response) {
  			if(response.error) {
  				$(document).trigger('status.contacts.error', response);
  			} else {
  				$(document).trigger('status.addressbook.activated', {
  					addressbook: self,
  					state: state
  				});
  			}
  			cb(response);
  		});
  	};
  
  	/**
  	 * Delete a list of contacts from the data store
  	 * @param array contactsIds An array of contact ids to be deleted.
  	 * @param cb Optional callback function which will be passed:
  	 * @return An object with a boolean variable 'error'.
  	 */
  	AddressBook.prototype.deleteContacts = function(contactsIds, cb) {
  		console.log('deleteContacts', contactsIds);
  		return $.when(this.storage.deleteContacts(this.getBackend(), this.getId(), contactsIds))
  			.then(function(response) {
  			if(response.error) {
  				$(document).trigger('status.contacts.error', response);
  			}
6d9380f96   Cédric Dupont   Update sources OC...
295
296
297
  			if(typeof cb === 'function') {
  				cb(response);
  			}
d1bafeea1   Kload   [fix] Upgrade to ...
298
299
300
301
302
  		});
  	};
  
  	/**
  	 * Delete address book from data store and remove it from the DOM
d1bafeea1   Kload   [fix] Upgrade to ...
303
304
  	 * @return An object with a boolean variable 'error'.
  	 */
6d9380f96   Cédric Dupont   Update sources OC...
305
  	AddressBook.prototype.destroy = function() {
d1bafeea1   Kload   [fix] Upgrade to ...
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
  		var self = this;
  		$.when(this.storage.deleteAddressBook(this.getBackend(), self.getId()))
  			.then(function(response) {
  			if(!response.error) {
  				self.$li.remove();
  				$(document).trigger('status.addressbook.removed', {
  					addressbook: self
  				});
  			} else {
  				$(document).trigger('status.contacts.error', response);
  			}
  		}).fail(function(response) {
  			console.log(response.message);
  			$(document).trigger('status.contacts.error', response);
  		});
  	};
  
  	/**
  	 * Controls access to address books
  	 */
  	var AddressBookList = function(
  			storage,
  			bookTemplate,
  			bookItemTemplate,
  			isFileAction
6d9380f96   Cédric Dupont   Update sources OC...
331
  		) {
d1bafeea1   Kload   [fix] Upgrade to ...
332
333
334
335
336
337
338
  		var self = this;
  		this.isFileAction = isFileAction || false;
  		this.storage = storage;
  		this.$bookTemplate = bookTemplate;
  		this.$bookList = this.$bookTemplate.find('.addressbooklist');
  		this.$bookItemTemplate = bookItemTemplate;
  		this.$importIntoSelect = this.$bookTemplate.find('#import_into');
6d9380f96   Cédric Dupont   Update sources OC...
339
  		this.$importFormatSelect = this.$bookTemplate.find('#import_format');
d1bafeea1   Kload   [fix] Upgrade to ...
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
  		this.$importProgress = this.$bookTemplate.find('#import-status-progress');
  		this.$importStatusText = this.$bookTemplate.find('#import-status-text');
  		this.addressBooks = [];
  
  		if(this.isFileAction) {
  			return;
  		}
  		this.$importFileInput = this.$bookTemplate.find('#import_upload_start');
  		var $addInput = this.$bookTemplate.find('#add-address-book');
  		$addInput.addnew({
  			ok: function(event, name) {
  				console.log('add-address-book ok', name);
  				$addInput.addClass('loading');
  				self.add(name, function(response) {
  					console.log('response', response);
  					if(response.error) {
  						$(document).trigger('status.contacts.error', response);
  					} else {
  						$(this).addnew('close');
  					}
  					$addInput.removeClass('loading');
  				});
  			}
  		});
  
  		$(document).bind('status.addressbook.removed', function(e, data) {
  			var addressBook = data.addressbook;
  			self.addressBooks.splice(self.addressBooks.indexOf(addressBook), 1);
  			self.buildImportSelect();
  		});
6d9380f96   Cédric Dupont   Update sources OC...
370
  		$(document).bind('status.addressbook.added', function() {
d1bafeea1   Kload   [fix] Upgrade to ...
371
  			self.buildImportSelect();
6d9380f96   Cédric Dupont   Update sources OC...
372
373
374
  		})
  		this.$importFormatSelect.on('change', function() {
  			self.$importIntoSelect.trigger('change');
d1bafeea1   Kload   [fix] Upgrade to ...
375
376
377
378
379
380
  		});
  		this.$importIntoSelect.on('change', function() {
  			// Disable file input if no address book selected
  			var value = $(this).val();
  			self.$importFileInput.prop('disabled', value === '-1' );
  			if(value !== '-1') {
6d9380f96   Cédric Dupont   Update sources OC...
381
382
383
384
385
386
387
  				var url = OC.generateUrl(
  					'apps/contacts/addressbook/{backend}/{addressBookId}/{importType}/import/upload',
  					{
  						addressBookId:value,
  						importType:self.$importFormatSelect.find('option:selected').val(),
  						backend: $(this).find('option:selected').data('backend')
  					}
d1bafeea1   Kload   [fix] Upgrade to ...
388
389
  				);
  				self.$importFileInput.fileupload('option', 'url', url);
d1bafeea1   Kload   [fix] Upgrade to ...
390
391
392
393
  			}
  		});
  		this.$importFileInput.fileupload({
  			dataType: 'json',
6d9380f96   Cédric Dupont   Update sources OC...
394
  			start: function(/*e, data*/) {
d1bafeea1   Kload   [fix] Upgrade to ...
395
396
397
398
399
  				self.$importProgress.progressbar({value:false});
  				$('.tipsy').remove();
  				$('.import-upload').hide();
  				$('.import-status').show();
  				self.$importProgress.fadeIn();
6d9380f96   Cédric Dupont   Update sources OC...
400
  				self.$importStatusText.text(t('contacts', 'Starting file import'));
d1bafeea1   Kload   [fix] Upgrade to ...
401
402
  			},
  			done: function (e, data) {
6d9380f96   Cédric Dupont   Update sources OC...
403
404
405
406
407
408
  				if ($('#import_format').find('option:selected').val() != 'automatic') {
  					$('#import-status-text').text(t('contacts', 'Format selected: {format}',
  													{format: $('#import_format').find('option:selected').text() }));
  				} else {
  					$('#import-status-text').text(t('contacts', 'Automatic format detection'));
  				}
d1bafeea1   Kload   [fix] Upgrade to ...
409
  				console.log('Upload done:', data);
6d9380f96   Cédric Dupont   Update sources OC...
410
  				self.doImport(self.storage.formatResponse(data.jqXHR));
d1bafeea1   Kload   [fix] Upgrade to ...
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
  			},
  			fail: function(e, data) {
  				console.log('fail', data);
  				OC.notify({message:data.errorThrown + ': ' + data.textStatus});
  				$('.import-upload').show();
  				$('.import-status').hide();
  			}
  		});
  	};
  
  	AddressBookList.prototype.count = function() {
  		return this.addressBooks.length;
  	};
  
  	/**
  	 * For importing from oC filesyatem
  	 */
6d9380f96   Cédric Dupont   Update sources OC...
428
429
  	AddressBookList.prototype.prepareImport = function(backend, addressBookId, importType, path, fileName) {
  		console.log('prepareImport', backend, addressBookId, importType, path, fileName);
d1bafeea1   Kload   [fix] Upgrade to ...
430
  		this.$importProgress.progressbar({value:false});
6d9380f96   Cédric Dupont   Update sources OC...
431
432
433
434
435
436
  		if (importType != 'automatic') {
  			this.$importStatusText.text(t('contacts', 'Format selected: {format}',
  											{format: self.$importFormatSelect.find('option:selected').val() }));
  		} else {
  			this.$importStatusText.text(t('contacts', 'Automatic format detection'));
  		}
d1bafeea1   Kload   [fix] Upgrade to ...
437
  		return this.storage.prepareImport(
6d9380f96   Cédric Dupont   Update sources OC...
438
  				backend, addressBookId, importType,
d1bafeea1   Kload   [fix] Upgrade to ...
439
440
441
442
443
  				{filename:fileName, path:path}
  			);
  	};
  
  	AddressBookList.prototype.doImport = function(response) {
6d9380f96   Cédric Dupont   Update sources OC...
444
  		console.log('doImport', response);
d1bafeea1   Kload   [fix] Upgrade to ...
445
446
447
448
449
450
451
452
453
454
455
456
457
458
  		var defer = $.Deferred();
  		var done = false;
  		var interval = null, isChecking = false;
  		var self = this;
  		var closeImport = function() {
  			defer.resolve();
  			self.$importProgress.fadeOut();
  			setTimeout(function() {
  				$('.import-upload').show();
  				$('.import-status').hide();
  				self.importCount = null;
  				if(self.$importProgress.hasClass('ui-progressbar')) {
  					self.$importProgress.progressbar('destroy');
  				}
6d9380f96   Cédric Dupont   Update sources OC...
459
  			}, 3000);
d1bafeea1   Kload   [fix] Upgrade to ...
460
461
  		};
  		if(!response.error) {
d1bafeea1   Kload   [fix] Upgrade to ...
462
  			this.$importProgress.progressbar('value', 0);
d1bafeea1   Kload   [fix] Upgrade to ...
463
  			var data = response.data;
6d9380f96   Cédric Dupont   Update sources OC...
464
  			var getStatus = function(backend, addressbookid, importType, progresskey, interval, done) {
d1bafeea1   Kload   [fix] Upgrade to ...
465
466
467
468
469
470
471
472
473
474
475
  				if(done) {
  					clearInterval(interval);
  					closeImport();
  					return;
  				}
  				if(isChecking) {
  					return;
  				}
  				isChecking = true;
  				$.when(
  					self.storage.importStatus(
6d9380f96   Cédric Dupont   Update sources OC...
476
  						backend, addressbookid, importType,
d1bafeea1   Kload   [fix] Upgrade to ...
477
478
479
480
  						{progresskey:progresskey}
  					))
  				.then(function(response) {
  					if(!response.error) {
6d9380f96   Cédric Dupont   Update sources OC...
481
482
483
484
485
486
487
  						console.log('status, response: ', response);
  						if (response.data.total != null && response.data.progress != null) {
  							self.$importProgress.progressbar('option', 'max', Number(response.data.total));
  							self.$importProgress.progressbar('value', Number(response.data.progress));
  							self.$importStatusText.text(t('contacts', 'Processing {count}/{total} cards',
  														{count: response.data.progress, total: response.data.total}));
  						}
d1bafeea1   Kload   [fix] Upgrade to ...
488
489
490
491
492
493
494
495
496
497
498
499
500
  					} else {
  						console.warn('Error', response.message);
  						self.$importStatusText.text(response.message);
  					}
  					isChecking = false;
  				}).fail(function(response) {
  					console.log(response.message);
  					$(document).trigger('status.contacts.error', response);
  					isChecking = false;
  				});
  			};
  			$.when(
  				self.storage.startImport(
6d9380f96   Cédric Dupont   Update sources OC...
501
  					data.backend, data.addressBookId, data.importType,
d1bafeea1   Kload   [fix] Upgrade to ...
502
  					{filename:data.filename, progresskey:data.progresskey}
6d9380f96   Cédric Dupont   Update sources OC...
503
504
  				)
  			)
d1bafeea1   Kload   [fix] Upgrade to ...
505
506
507
508
  			.then(function(response) {
  				console.log('response', response);
  				if(!response.error) {
  					console.log('Import done');
6d9380f96   Cédric Dupont   Update sources OC...
509
510
  					self.$importStatusText.text(t('contacts', 'Total:{total}, Success:{imported}, Errors:{failed}',
  													  {total: response.data.total, imported:response.data.imported, failed: response.data.failed}));
d1bafeea1   Kload   [fix] Upgrade to ...
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
  					var addressBook = self.find({id:response.data.addressBookId, backend: response.data.backend});
  					$(document).trigger('status.addressbook.imported', {
  						addressbook: addressBook
  					});
  					defer.resolve();
  				} else {
  					defer.reject(response);
  					self.$importStatusText.text(response.message);
  					$(document).trigger('status.contacts.error', response);
  				}
  				done = true;
  			}).fail(function(response) {
  				defer.reject(response);
  				console.log(response.message);
  				$(document).trigger('status.contacts.error', response);
  				done = true;
  			});
  			interval = setInterval(function() {
6d9380f96   Cédric Dupont   Update sources OC...
529
  				getStatus(data.backend, data.addressBookId, data.importType, data.progresskey, interval, done);
d1bafeea1   Kload   [fix] Upgrade to ...
530
531
532
533
534
535
536
537
538
  			}, 1500);
  		} else {
  			defer.reject(response);
  			done = true;
  			self.$importStatusText.text(response.message);
  			closeImport();
  			$(document).trigger('status.contacts.error', response);
  		}
  		return defer;
6d9380f96   Cédric Dupont   Update sources OC...
539
  	};
d1bafeea1   Kload   [fix] Upgrade to ...
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
  
  	/**
  	 * Rebuild the select to choose which address book to import into.
  	 */
  	AddressBookList.prototype.buildImportSelect = function() {
  		console.log('buildImportSelect');
  		var self = this;
  		this.$importIntoSelect.find('option:not([value="-1"])').remove();
  		var addressBooks = this.selectByPermission(OC.PERMISSION_UPDATE);
  		$.each(addressBooks, function(idx, book) {
  			var $opt = $('<option />');
  			$opt.val(book.getId()).text(book.getDisplayName()).data('backend', book.getBackend());
  			self.$importIntoSelect.append($opt);
  			console.log('appending', $opt, 'to', self.$importIntoSelect);
  		});
  		if(!this.isFileAction) {
  			if(addressBooks.length === 1) {
  				this.$importIntoSelect.val(this.$importIntoSelect.find('option:not([value="-1"])').first().val()).hide().trigger('change');
  				self.$importFileInput.prop('disabled', false);
  			} else {
  				this.$importIntoSelect.show();
  				self.$importFileInput.prop('disabled', true);
  			}
  		}
6d9380f96   Cédric Dupont   Update sources OC...
564
  	};
d1bafeea1   Kload   [fix] Upgrade to ...
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
  
  	/**
  	 * Create an AddressBook object, save it in internal list and append it's rendered result to the list
  	 *
  	 * @param object addressBook
  	 * @param bool rebuild If true rebuild the address book select for import.
  	 * @return AddressBook
  	 */
  	AddressBookList.prototype.insertAddressBook = function(addressBook) {
  		var book = new AddressBook(this.storage, addressBook, this.$bookItemTemplate, this.isFileAction);
  		if(!this.isFileAction) {
  			var result = book.render();
  			this.$bookList.append(result);
  		}
  		this.addressBooks.push(book);
  		return book;
  	};
  
  	/**
  	 * Get an AddressBook
  	 *
  	 * @param object info An object with the string  properties 'id' and 'backend'
  	 * @return AddressBook|null
  	 */
  	AddressBookList.prototype.find = function(info) {
  		console.log('AddressBookList.find', info);
  		var addressBook = null;
  		$.each(this.addressBooks, function(idx, book) {
  			if(book.getId() === String(info.id) && book.getBackend() === info.backend) {
  				addressBook = book;
  				return false; // break loop
  			}
  		});
  		return addressBook;
6d9380f96   Cédric Dupont   Update sources OC...
599
  	};
d1bafeea1   Kload   [fix] Upgrade to ...
600
601
602
603
604
605
606
607
608
609
  
  	/**
  	 * Move a contacts from one address book to another..
  	 *
  	 * @param Contact The contact to move
  	 * @param object from An object with properties 'id' and 'backend'.
  	 * @param object target An object with properties 'id' and 'backend'.
  	 */
  	AddressBookList.prototype.moveContact = function(contact, from, target) {
  		console.log('AddressBookList.moveContact, contact', contact, from, target);
d1bafeea1   Kload   [fix] Upgrade to ...
610
611
612
613
614
615
616
617
618
619
620
621
  		$.when(this.storage.moveContact(from.backend, from.id, contact.getId(), {target:target}))
  			.then(function(response) {
  			if(!response.error) {
  				console.log('Contact moved', response);
  				$(document).trigger('status.contact.moved', {
  					contact: contact,
  					data: response.data
  				});
  			} else {
  				$(document).trigger('status.contacts.error', response);
  			}
  		});
6d9380f96   Cédric Dupont   Update sources OC...
622
  	};
d1bafeea1   Kload   [fix] Upgrade to ...
623
624
625
626
627
628
629
630
631
  
  	/**
  	 * Get an array of address books with at least the required permission.
  	 *
  	 * @param int permission
  	 * @param bool noClone If true the original objects will be returned and can be manipulated.
  	 */
  	AddressBookList.prototype.selectByPermission = function(permission, noClone) {
  		var books = [];
d1bafeea1   Kload   [fix] Upgrade to ...
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
  		$.each(this.addressBooks, function(idx, book) {
  			if(book.getPermissions() & permission) {
  				// Clone the address book not to mess with with original
  				books.push(noClone ? book : $.extend(true, {}, book));
  			}
  		});
  		return books;
  	};
  
  	/**
  	 * Add a new address book.
  	 *
  	 * @param string name
  	 * @param function cb
  	 * @return jQuery.Deferred
  	 * @throws Error
  	 */
  	AddressBookList.prototype.add = function(name, cb) {
  		console.log('AddressBookList.add', name, typeof cb);
  		var defer = $.Deferred();
  		// Check for wrong, duplicate or empty name
  		if(typeof name !== 'string') {
  			throw new TypeError('BadArgument: AddressBookList.add() only takes String arguments.');
  		}
  		if(name.trim() === '') {
  			throw new Error('BadArgument: Cannot add an address book with an empty name.');
  		}
  		var error = '';
  		$.each(this.addressBooks, function(idx, book) {
6d9380f96   Cédric Dupont   Update sources OC...
661
  			if(book.getDisplayName() === name) {
d1bafeea1   Kload   [fix] Upgrade to ...
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
  				console.log('Dupe');
  				error = t('contacts', 'An address book called {name} already exists', {name:name});
  				if(typeof cb === 'function') {
  					cb({error:true, message:error});
  				}
  				defer.reject({error:true, message:error});
  				return false; // break loop
  			}
  		});
  		if(error.length) {
  			console.warn('Error:', error);
  			return defer;
  		}
  		var self = this;
  		$.when(this.storage.addAddressBook('local',
  		{displayname: name, description: ''})).then(function(response) {
  			if(response.error) {
  				error = response.message;
  				if(typeof cb === 'function') {
  					cb({error:true, message:error});
  				}
  				defer.reject(response);
  			} else {
  				var book = self.insertAddressBook(response.data);
  				$(document).trigger('status.addressbook.added');
  				if(typeof cb === 'function') {
  					cb({error:false, addressbook: book});
  				}
  				defer.resolve({error:false, addressbook: book});
  			}
  		})
  		.fail(function(jqxhr, textStatus, error) {
  			$(this).removeClass('loading');
  			var err = textStatus + ', ' + error;
6d9380f96   Cédric Dupont   Update sources OC...
696
  			console.log('Request Failed', + err);
d1bafeea1   Kload   [fix] Upgrade to ...
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
  			error = t('contacts', 'Failed adding address book: {error}', {error:err});
  			if(typeof cb === 'function') {
  				cb({error:true, message:error});
  			}
  			defer.reject({error:true, message:error});
  		});
  		return defer;
  	};
  
  	/**
  	* Load address books
  	*/
  	AddressBookList.prototype.loadAddressBooks = function() {
  		var self = this;
  		var defer = $.Deferred();
  		$.when(this.storage.getAddressBooksForUser()).then(function(response) {
  			if(!response.error) {
d1bafeea1   Kload   [fix] Upgrade to ...
714
  				$.each(response.data.addressbooks, function(idx, addressBook) {
6d9380f96   Cédric Dupont   Update sources OC...
715
  					self.insertAddressBook(addressBook);
d1bafeea1   Kload   [fix] Upgrade to ...
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
  				});
  				self.buildImportSelect();
  				console.log('After buildImportSelect');
  				if(!self.isFileAction) {
  					if(typeof OC.Share !== 'undefined') {
  						OC.Share.loadIcons('addressbook');
  					} else {
  						self.$bookList.find('a.action.share').css('display', 'none');
  					}
  				}
  				console.log('Before resolve');
  				defer.resolve(self.addressBooks);
  				console.log('After resolve');
  			} else {
  				defer.reject(response);
  				$(document).trigger('status.contacts.error', response);
  			}
  		})
  		.fail(function(response) {
6d9380f96   Cédric Dupont   Update sources OC...
735
  			console.warn('Request Failed:', response);
d1bafeea1   Kload   [fix] Upgrade to ...
736
737
738
739
740
741
742
743
744
745
746
  			defer.reject({
  				error: true,
  				message: t('contacts', 'Failed loading address books: {error}', {error:response.message})
  			});
  		});
  		return defer.promise();
  	};
  
  	OC.Contacts.AddressBookList = AddressBookList;
  
  })(window, jQuery, OC);