Пример #1
0
  @Override
  protected void listRemote() throws IOException, HttpException, DavException {
    // fetch list of remote VCards and build hash table to index file name

    try {
      davAddressBook().addressbookQuery();
    } catch (HttpException e) {
      /*  non-successful responses to CARDDAV:addressbook-query with empty filter, tested on 2015/10/21
       *  fastmail.com                 403 Forbidden (DAV:error CARDDAV:supported-filter)
       *  mailbox.org (OpenXchange)    400 Bad Request
       *  SOGo                         207 Multi-status, but without entries       http://www.sogo.nu/bugs/view.php?id=3370
       *  Zimbra ZCS                   500 Server Error                            https://bugzilla.zimbra.com/show_bug.cgi?id=101902
       */
      if (e.status == 400 || e.status == 403 || e.status == 500 || e.status == 501) {
        App.log.log(
            Level.WARNING, "Server error on REPORT addressbook-query, falling back to PROPFIND", e);
        davAddressBook().propfind(1, GetETag.NAME);
      } else
        // no defined fallback, pass through exception
        throw e;
    }

    remoteResources = new HashMap<>(davCollection.members.size());
    for (DavResource vCard : davCollection.members) {
      String fileName = vCard.fileName();
      App.log.fine("Found remote VCard: " + fileName);
      remoteResources.put(fileName, vCard);
    }
  }
Пример #2
0
  @Override
  protected void downloadRemote()
      throws IOException, HttpException, DavException, ContactsStorageException {
    App.log.info("Downloading " + toDownload.size() + " contacts (" + MAX_MULTIGET + " at once)");

    // prepare downloader which may be used to download external resource like contact photos
    Contact.Downloader downloader = new ResourceDownloader(collectionURL);

    // download new/updated VCards from server
    for (DavResource[] bunch :
        ArrayUtils.partition(
            toDownload.toArray(new DavResource[toDownload.size()]), MAX_MULTIGET)) {
      if (Thread.interrupted()) return;

      App.log.info("Downloading " + StringUtils.join(bunch, ", "));

      if (bunch.length == 1) {
        // only one contact, use GET
        DavResource remote = bunch[0];

        ResponseBody body =
            remote.get("text/vcard;version=4.0, text/vcard;charset=utf-8;q=0.8, text/vcard;q=0.5");
        String eTag = ((GetETag) remote.properties.get(GetETag.NAME)).eTag;

        Charset charset = Charsets.UTF_8;
        MediaType contentType = body.contentType();
        if (contentType != null) charset = contentType.charset(Charsets.UTF_8);

        @Cleanup InputStream stream = body.byteStream();
        processVCard(remote.fileName(), eTag, stream, charset, downloader);

      } else {
        // multiple contacts, use multi-get
        List<HttpUrl> urls = new LinkedList<>();
        for (DavResource remote : bunch) urls.add(remote.location);
        davAddressBook().multiget(urls.toArray(new HttpUrl[urls.size()]), hasVCard4);

        // process multiget results
        for (DavResource remote : davCollection.members) {
          String eTag;
          GetETag getETag = (GetETag) remote.properties.get(GetETag.NAME);
          if (getETag != null) eTag = getETag.eTag;
          else throw new DavException("Received multi-get response without ETag");

          Charset charset = Charsets.UTF_8;
          GetContentType getContentType =
              (GetContentType) remote.properties.get(GetContentType.NAME);
          if (getContentType != null && getContentType.type != null) {
            MediaType type = MediaType.parse(getContentType.type);
            if (type != null) charset = type.charset(Charsets.UTF_8);
          }

          AddressData addressData = (AddressData) remote.properties.get(AddressData.NAME);
          if (addressData == null || addressData.vCard == null)
            throw new DavException("Received multi-get response without address data");

          @Cleanup InputStream stream = new ByteArrayInputStream(addressData.vCard.getBytes());
          processVCard(remote.fileName(), eTag, stream, charset, downloader);
        }
      }
    }
  }