Beispiel #1
0
  /* recursively
  (i) create new Parts for each thing listed
  in the relationships
  (ii) add the new Part to the package
  (iii) cross the PartName off unusedZipEntries
  */
  private void addPartsFromRelationships(Base source, RelationshipsPart rp, ContentTypeManager ctm)
      throws Docx4JException {

    OpcPackage pkg = source.getPackage();

    for (Relationship r : rp.getRelationships().getRelationship()) {

      log.debug(
          "\n For Relationship Id="
              + r.getId()
              + " Source is "
              + rp.getSourceP().getPartName()
              + ", Target is "
              + r.getTarget()
              + ", type: "
              + r.getType());

      // This is usually the first logged comment for
      // a part, so start with a line break.
      try {
        getPart(pkg, rp, r, ctm);
      } catch (Exception e) {
        throw new Docx4JException("Failed to add parts from relationships", e);
      }
    }
  }
Beispiel #2
0
  /**
   * Creates document header including process name
   *
   * @param doc WordprocessingMLPackage for the document.
   * @throws InvalidFormatException
   */
  private void createHeader(WordprocessingMLPackage doc) throws InvalidFormatException {
    MainDocumentPart content = doc.getMainDocumentPart();

    // Create header
    HeaderPart header = new HeaderPart();
    Relationship rel = content.addTargetPart(header);

    Hdr hdr = objectFactory.createHdr();

    P headerParagraph = content.createParagraphOfText(p.getTitle());
    hdr.getContent().add(headerParagraph);
    header.setJaxbElement(hdr);

    setStyle(headerParagraph, "Header");
    alignParagraph(headerParagraph, JcEnumeration.CENTER);

    // Relate to document
    List<SectionWrapper> sections = doc.getDocumentModel().getSections();
    SectPr sectPr = sections.get(sections.size() - 1).getSectPr();

    if (null == sectPr) {
      sectPr = objectFactory.createSectPr();
      content.addObject(sectPr);
      sections.get(sections.size() - 1).setSectPr(sectPr);
    }

    HeaderReference headerReference = objectFactory.createHeaderReference();
    headerReference.setId(rel.getId());
    headerReference.setType(HdrFtrRef.DEFAULT);
    sectPr.getEGHdrFtrReferences().add(headerReference);
  }
Beispiel #3
0
  /**
   * Nastaví záhlaví dokumentu. Úprava předchozí funkce.
   *
   * @param irPackage
   * @throws InvalidFormatException
   */
  private Ftr SetupFooter(WordprocessingMLPackage irPackage) throws InvalidFormatException {
    ObjectFactory lrFactory = Context.getWmlObjectFactory();

    /* create header part */
    FooterPart lrFooterPart = new FooterPart();
    lrFooterPart.setPackage(irPackage);

    Ftr lrFooter = lrFactory.createFtr();

    lrFooterPart.setJaxbElement(lrFooter);
    Relationship lrRelationship = irPackage.getMainDocumentPart().addTargetPart(lrFooterPart);
    /* end create header part */

    /* create header reference */
    List<SectionWrapper> lrSections = irPackage.getDocumentModel().getSections();
    SectPr lrSectionPr = lrSections.get(lrSections.size() - 1).getSectPr();
    // There is always a section wrapper, but it might not contain a sectPr
    if (lrSectionPr == null) {
      lrSectionPr = lrFactory.createSectPr();
      irPackage.getMainDocumentPart().addObject(lrSectionPr);
      lrSections.get(lrSections.size() - 1).setSectPr(lrSectionPr);
    }

    FooterReference lrFooterReference = lrFactory.createFooterReference();
    lrFooterReference.setId(lrRelationship.getId());
    lrFooterReference.setType(HdrFtrRef.DEFAULT);
    lrSectionPr.getEGHdrFtrReferences().add(lrFooterReference); // add header or footer references
    /* end create header reference */

    return lrFooter;
  }
Beispiel #4
0
  /**
   * Creates document footer including page number
   *
   * @param doc WordprocessingMLPackage for the document.
   * @throws InvalidFormatException
   */
  private void createFooter(WordprocessingMLPackage doc) throws InvalidFormatException {
    MainDocumentPart content = doc.getMainDocumentPart();

    // Create footer
    FooterPart footer = new FooterPart();

    Ftr ftr = objectFactory.createFtr();
    P footerParagraph = objectFactory.createP();

    setStyle(footerParagraph, "footer");

    PPr parProps = objectFactory.createPPr();
    Jc al = objectFactory.createJc();
    al.setVal(JcEnumeration.RIGHT);
    parProps.setJc(al);
    footerParagraph.setPPr(parProps);

    // Add field start
    R run = objectFactory.createR();
    FldChar fldChar = objectFactory.createFldChar();
    fldChar.setFldCharType(STFldCharType.BEGIN);
    run.getContent().add(fldChar);
    footerParagraph.getContent().add(run);

    // Add pageNumber field
    run = objectFactory.createR();
    Text txt = objectFactory.createText();
    txt.setSpace("preserve");
    txt.setValue(" PAGE   \\* MERGEFORMAT ");
    run.getContent().add(objectFactory.createRInstrText(txt));
    footerParagraph.getContent().add(run);

    // Add field end
    run = objectFactory.createR();
    fldChar = objectFactory.createFldChar();
    fldChar.setFldCharType(STFldCharType.END);
    run.getContent().add(fldChar);
    footerParagraph.getContent().add(run);

    ftr.getContent().add(footerParagraph);
    footer.setJaxbElement(ftr);

    Relationship rel = content.addTargetPart(footer);

    // Relate footer to document
    List<SectionWrapper> sections = doc.getDocumentModel().getSections();

    SectPr sectPr = sections.get(sections.size() - 1).getSectPr();

    if (null == sectPr) {
      sectPr = objectFactory.createSectPr();
      content.addObject(sectPr);
      sections.get(sections.size() - 1).setSectPr(sectPr);
    }

    FooterReference footerReference = objectFactory.createFooterReference();
    footerReference.setId(rel.getId());
    footerReference.setType(HdrFtrRef.DEFAULT);
    sectPr.getEGHdrFtrReferences().add(footerReference);
  }
 protected static void removeDefinedCustomXmlParts(
     WordprocessingMLPackage wmlPackage, String xpathStorageItemId) {
   List<PartName> partsToRemove = new ArrayList<PartName>();
   RelationshipsPart relationshipsPart = wmlPackage.getMainDocumentPart().getRelationshipsPart();
   List<Relationship> relationshipsList =
       ((relationshipsPart != null) && (relationshipsPart.getRelationships() != null)
           ? relationshipsPart.getRelationships().getRelationship()
           : null);
   Part part = null;
   CustomXmlDataStoragePart dataPart = null;
   if (relationshipsList != null) {
     for (Relationship relationship : relationshipsList) {
       if (Namespaces.CUSTOM_XML_DATA_STORAGE.equals(relationship.getType())) {
         part = relationshipsPart.getPart(relationship);
         if (IsPartToRemove(part, xpathStorageItemId)) {
           partsToRemove.add(part.getPartName());
         }
       }
     }
   }
   if (!partsToRemove.isEmpty()) {
     for (int i = 0; i < partsToRemove.size(); i++) {
       relationshipsPart.removePart(partsToRemove.get(i));
     }
   }
 }
Beispiel #6
0
  private static void addPartsForRels(
      List<Alteration> list, List<Relationship> rels, RelationshipsPart rp) throws Docx4JException {

    for (Relationship r : rels) {
      if (r.getTargetMode() != null && r.getTargetMode().equals("External")) {
        log.debug(r.getTarget() + " is external");
        // Have everything we need info wise in transmitting the rels part
      } else {
        list.add(new Alteration(rp, toStorageFormat(rp.getPart(r))));
        log.debug("added part: " + r.getTarget());
      }
    }
  }
  // private void addPartsFromRelationships(ZipFile zf, Base source, RelationshipsPart rp)
  private void addPartsFromRelationships(
      HashMap<String, ByteArray> partByteArrays,
      Base source,
      RelationshipsPart rp,
      ContentTypeManager ctm)
      throws Docx4JException {

    OpcPackage pkg = source.getPackage();

    //		for (Iterator it = rp.iterator(); it.hasNext(); ) {
    //			Relationship r = (Relationship)it.next();
    //			log.info("For Relationship Id=" + r.getId() + " Source is "
    //					+ r.getSource().getPartName()
    //					+ ", Target is " + r.getTargetURI() );
    //			try {
    //
    //				getPart(zf, pkg, rp, r);
    //
    //			} catch (Exception e) {
    //				throw new Docx4JException("Failed to add parts from relationships", e);
    //			}
    //		}

    for (Relationship r : rp.getRelationships().getRelationship()) {

      log.debug(
          "\n For Relationship Id="
              + r.getId()
              + " Source is "
              + rp.getSourceP().getPartName()
              + ", Target is "
              + r.getTarget()
              + ", type: "
              + r.getType());

      // This is usually the first logged comment for
      // a part, so start with a line break.
      try {
        getPart(partByteArrays, pkg, rp, r, ctm);
      } catch (Exception e) {
        throw new Docx4JException("Failed to add parts from relationships", e);
      }
    }
  }
  protected static Set<ContentAccessor> getParts(WordprocessingMLPackage srcPackage) {

    Set<ContentAccessor> partList = new HashSet<ContentAccessor>();

    partList.add(srcPackage.getMainDocumentPart());

    // Add headers/footers
    RelationshipsPart rp = srcPackage.getMainDocumentPart().getRelationshipsPart();
    for (Relationship r : rp.getRelationships().getRelationship()) {

      if (r.getType().equals(Namespaces.HEADER)) {
        partList.add((HeaderPart) rp.getPart(r));
      } else if (r.getType().equals(Namespaces.FOOTER)) {
        partList.add((FooterPart) rp.getPart(r));
      }
    }

    return partList;
  }
  protected static boolean IsPartToRemove(Part part, String xpathStorageItemId) {
    boolean ret = false;
    RelationshipsPart relationshipsPart = part.getRelationshipsPart();
    List<Relationship> relationshipsList =
        ((relationshipsPart != null) && (relationshipsPart.getRelationships() != null)
            ? relationshipsPart.getRelationships().getRelationship()
            : null);

    CustomXmlDataStoragePropertiesPart propertiesPart = null;
    DatastoreItem datastoreItem = null;
    if ((relationshipsList != null) && (!relationshipsList.isEmpty())) {
      for (Relationship relationship : relationshipsList) {
        if (Namespaces.CUSTOM_XML_DATA_STORAGE_PROPERTIES.equals(relationship.getType())) {
          propertiesPart =
              (CustomXmlDataStoragePropertiesPart) relationshipsPart.getPart(relationship);
          break;
        }
      }
    }
    if (propertiesPart != null) {
      datastoreItem = propertiesPart.getJaxbElement();
    }
    if (datastoreItem != null) {
      if ((datastoreItem.getItemID() != null) && (datastoreItem.getItemID().length() > 0)) {
        ret = datastoreItem.getItemID().equals(xpathStorageItemId);
      }
      if ((!ret)
          && (datastoreItem.getSchemaRefs() != null)
          && (datastoreItem.getSchemaRefs().getSchemaRef() != null)
          && (!datastoreItem.getSchemaRefs().getSchemaRef().isEmpty())) {
        for (SchemaRef ref : datastoreItem.getSchemaRefs().getSchemaRef()) {
          if (PART_TO_REMOVE_SCHEMA_TYPES.contains(ref.getUri())) {
            ret = true;
            break;
          }
        }
      }
    }
    return ret;
  }
Beispiel #10
0
  /**
   * @param alteredParts
   * @param theseRels
   * @throws Docx4JException
   */
  private static void addTree(List<Alteration> list, RelationshipsPart rp) throws Docx4JException {

    if (rp == null) return;

    for (Relationship r : rp.getJaxbElement().getRelationship()) {
      if (r.getTargetMode() != null && r.getTargetMode().equals("External")) {
        log.debug(r.getTarget() + " is external");
        // Have everything we need info wise in transmitting the rels part
      } else {
        list.add(new Alteration(rp, toStorageFormat(rp.getPart(r))));
        log.debug("add tree: " + r.getTarget());

        // recurse
        Part nextSourcePart = rp.getPart(r);
        RelationshipsPart nextRP = nextSourcePart.getRelationshipsPart();
        if (nextRP != null) {
          list.add(new Alteration(nextSourcePart.getPartName(), toStorageFormat(nextRP)));
          addTree(list, nextRP);
        }
      }
    }
  }
  public org.docx4j.wml.P.Hyperlink newHyperlink(MainDocumentPart mdp, String text, String url) {
    try {
      // We need to add a relationship to word/_rels/document.xml.rels but since its external, we
      // don't use
      // the usual wordMLPackage.getMainDocumentPart().addTargetPart mechanism
      org.docx4j.relationships.ObjectFactory factory = new org.docx4j.relationships.ObjectFactory();
      org.docx4j.relationships.Relationship rel = factory.createRelationship();
      rel.setType(Namespaces.HYPERLINK);
      rel.setTarget(url);
      rel.setTargetMode("External");
      mdp.getRelationshipsPart().addRelationship(rel);
      // addRelationship sets the rel's @Id

      org.docx4j.wml.P.Hyperlink hyp = new org.docx4j.wml.P.Hyperlink();
      hyp.setId(rel.getId());
      R run = Context.getWmlObjectFactory().createR();
      hyp.getContent().add(run);
      RPr rpr = new RPr();
      RStyle rStyle = new RStyle();
      rStyle.setVal("Hyperlink");
      rpr.setRStyle(rStyle);
      run.setRPr(rpr);

      Text t = new Text();
      t.setValue(text);
      run.getContent().add(t);
      //			String hpl = "<w:hyperlink r:id=\"" + rel.getId()
      //					+ "\" xmlns:w=\"http://schemas.openxmlformats.org/wordprocessingml/2006/main\" "
      //					+ "xmlns:r=\"http://schemas.openxmlformats.org/officeDocument/2006/relationships\" >" +
      // "<w:r>" + "<w:rPr>"
      //					+ "<w:rStyle w:val=\"Hyperlink\" />" +
      //					"</w:rPr>" + "<w:t>" + text + "</w:t>" + "</w:r>" + "</w:hyperlink>";
      //			return (org.docx4j.wml.P.Hyperlink) XmlUtils.unmarshalString(hpl);
      return hyp;
    } catch (Exception e) {
      e.printStackTrace();
      return null;
    }
  }
 private void createFooterReference(
     WordprocessingMLPackage wordprocessingMLPackage, Relationship relationship)
     throws InvalidFormatException {
   List<SectionWrapper> sections = wordprocessingMLPackage.getDocumentModel().getSections();
   SectPr sectPr = sections.get(sections.size() - 1).getSectPr();
   // There is always a section wrapper, but it might not contain a sectPr
   if (sectPr == null) {
     sectPr = factory.createSectPr();
     wordprocessingMLPackage.getMainDocumentPart().addObject(sectPr);
     sections.get(sections.size() - 1).setSectPr(sectPr);
   }
   FooterReference footerReference = factory.createFooterReference();
   footerReference.setId(relationship.getId());
   footerReference.setType(HdrFtrRef.DEFAULT);
   sectPr.getEGHdrFtrReferences().add(footerReference);
 }
Beispiel #13
0
  public static void visit(
      WordprocessingMLPackage wmlPackage, boolean bodyOnly, Callback callback) {

    MainDocumentPart mainDocument = null;
    RelationshipsPart relPart = null;
    List<Relationship> relList = null;
    List<Object> elementList = null;

    if ((wmlPackage != null) && (callback != null)) {
      mainDocument = wmlPackage.getMainDocumentPart();
      callback.walkJAXBElements(mainDocument.getJaxbElement().getBody());
      if (!bodyOnly) {
        relPart = mainDocument.getRelationshipsPart();
        relList = relPart.getRelationships().getRelationship();
        for (Relationship rs : relList) {
          elementList = null;
          if (Namespaces.HEADER.equals(rs.getType())) {
            elementList = ((HeaderPart) relPart.getPart(rs)).getJaxbElement().getContent();
          } else if (Namespaces.FOOTER.equals(rs.getType())) {
            elementList = ((FooterPart) relPart.getPart(rs)).getJaxbElement().getContent();
          } else if (Namespaces.ENDNOTES.equals(rs.getType())) {
            // elementList = ((EndnotesPart) relPart.getPart(rs)).getContent();
            elementList = new ArrayList();
            elementList.addAll(((EndnotesPart) relPart.getPart(rs)).getJaxbElement().getEndnote());
          } else if (Namespaces.FOOTNOTES.equals(rs.getType())) {
            // elementList =  ((FootnotesPart) relPart.getPart(rs)).getContent();
            elementList = new ArrayList();
            elementList.addAll(
                ((FootnotesPart) relPart.getPart(rs)).getJaxbElement().getFootnote());
          } else if (Namespaces.COMMENTS.equals(rs.getType())) {
            elementList = new ArrayList();
            for (Comment comment :
                ((CommentsPart) relPart.getPart(rs)).getJaxbElement().getComment()) {
              elementList.addAll(comment.getEGBlockLevelElts());
            }
          }
          if ((elementList != null) && (!elementList.isEmpty())) {
            log.debug("Processing target: " + rs.getTarget() + ", type: " + rs.getType());
            callback.walkJAXBElements(elementList);
          }
        }
      }
    }
  }
Beispiel #14
0
  /* recursively
  	(i) get each Part listed in the relationships
  	(ii) add the Part to the zip file
  	(iii) traverse its relationship
  */
  public void addPartsFromRelationships(ZipOutputStream out, RelationshipsPart rp)
      throws Docx4JException {

    //		for (Iterator it = rp.iterator(); it.hasNext(); ) {
    //			Relationship r = (Relationship)it.next();
    //			log.info("For Relationship Id=" + r.getId() + " Source is " + r.getSource().getPartName() +
    // ", Target is " + r.getTargetURI() );
    for (Relationship r : rp.getRelationships().getRelationship()) {

      log.debug(
          "For Relationship Id="
              + r.getId()
              + " Source is "
              + rp.getSourceP().getPartName()
              + ", Target is "
              + r.getTarget());

      if (r.getType().equals(Namespaces.HYPERLINK)) {
        continue; // whether internal or external
      }

      if (r.getTargetMode() != null && r.getTargetMode().equals("External")) {

        // ie its EXTERNAL
        // As at 1 May 2008, we don't have a Part for these;
        // there is just the relationship.

        log.warn("Encountered external resource " + r.getTarget() + " of type " + r.getType());

        // So
        continue;
      }

      try {
        // String resolvedPartUri = URIHelper.resolvePartUri(r.getSourceURI(), r.getTargetURI()
        // ).toString();

        String resolvedPartUri =
            URIHelper.resolvePartUri(rp.getSourceURI(), new URI(r.getTarget())).toString();

        // Now drop leading "/'
        resolvedPartUri = resolvedPartUri.substring(1);

        // Now normalise it .. ie abc/def/../ghi
        // becomes abc/ghi
        // Maybe this isn't necessary with a zip file,
        // - ZipFile class may be smart enough to do it.
        // But it is certainly necessary in the JCR case.
        //				target = (new java.net.URI(target)).normalize().toString();
        //				log.info("Normalised, it is " + target );

        //				Document contents = getDocumentFromZippedPart( zf,  target);

        if (!false) {
          log.debug("Getting part /" + resolvedPartUri);

          // Part part = p.getParts().get(new PartName("/" + resolvedPartUri));
          Part part = rp.getPart(r);
          // 2012 09 26: If the part is actually attached to
          // a different package, using this you can still get it.
          // Use this 'feature' at your own risk!

          if (part == null) {
            log.error("Part " + resolvedPartUri + " not found!");
          } else {
            log.debug(part.getClass().getName());
          }

          if (!part.getPackage().equals(p)) {
            log.warn("Part " + resolvedPartUri + " is attached to some other package");
          }

          savePart(out, part);
        }

      } catch (Exception e) {
        throw new Docx4JException(
            "Failed to add parts from relationships of " + rp.getSourceP().getPartName(), e);
      }
    }
  }
Beispiel #15
0
  /**
   * Get a Part (except a relationships part), but not its relationships part or related parts.
   * Useful if you need quick access to just this part. This can be called directly from outside the
   * library, in which case the Part will not be owned by a Package until the calling code makes it
   * so.
   *
   * @see To get a Part and all its related parts, and add all to a package, use getPart.
   * @param partByteArrays
   * @param ctm
   * @param resolvedPartUri
   * @param rel
   * @return
   * @throws Docx4JException including if result is null
   */
  public Part getRawPart(ContentTypeManager ctm, String resolvedPartUri, Relationship rel)
      throws Docx4JException {

    Part part = null;

    InputStream is = null;
    try {
      try {
        log.debug("resolved uri: " + resolvedPartUri);

        // Get a subclass of Part appropriate for this content type
        // This will throw UnrecognisedPartException in the absence of
        // specific knowledge. Hence it is important to get the is
        // first, as we do above.
        part = ctm.getPart("/" + resolvedPartUri, rel);

        log.info("ctm returned " + part.getClass().getName());

        if (part instanceof org.docx4j.openpackaging.parts.ThemePart
            || part instanceof org.docx4j.openpackaging.parts.DocPropsCorePart
            || part instanceof org.docx4j.openpackaging.parts.DocPropsCustomPart
            || part instanceof org.docx4j.openpackaging.parts.DocPropsExtendedPart
            || part instanceof org.docx4j.openpackaging.parts.CustomXmlDataStoragePropertiesPart
            || part instanceof org.docx4j.openpackaging.parts.digitalsignature.XmlSignaturePart
            || part instanceof org.docx4j.openpackaging.parts.JaxbXmlPart) {

          // Nothing to do here

        } else if (part instanceof org.docx4j.openpackaging.parts.WordprocessingML.BinaryPart) {

          log.debug("Detected BinaryPart " + part.getClass().getName());
          //					is = partStore.loadPart( resolvedPartUri);
          //					((BinaryPart)part).setBinaryData(is);

        } else if (part instanceof org.docx4j.openpackaging.parts.CustomXmlDataStoragePart) {
          // ContentTypeManager initially detects them as CustomXmlDataStoragePart;
          // the below changes as necessary

          // Is it a part we know?
          is = partStore.loadPart(resolvedPartUri);
          try {
            Unmarshaller u = Context.jc.createUnmarshaller();
            Object o = u.unmarshal(is);
            log.debug(o.getClass().getName());

            PartName name = part.getPartName();
            if (o instanceof CoverPageProperties) {

              part = new DocPropsCoverPagePart(name);
              ((DocPropsCoverPagePart) part).setJaxbElement((CoverPageProperties) o);

            } else if (o instanceof org.opendope.conditions.Conditions) {

              part = new ConditionsPart(name);
              ((ConditionsPart) part).setJaxbElement((org.opendope.conditions.Conditions) o);

            } else if (o instanceof org.opendope.xpaths.Xpaths) {

              part = new XPathsPart(name);
              ((XPathsPart) part).setJaxbElement((org.opendope.xpaths.Xpaths) o);

            } else if (o instanceof org.opendope.questions.Questionnaire) {

              part = new QuestionsPart(name);
              ((QuestionsPart) part).setJaxbElement((org.opendope.questions.Questionnaire) o);

            } else if (o instanceof org.opendope.answers.Answers) {

              part = new StandardisedAnswersPart(name);
              ((StandardisedAnswersPart) part).setJaxbElement((org.opendope.answers.Answers) o);

            } else if (o instanceof org.opendope.components.Components) {

              part = new ComponentsPart(name);
              ((ComponentsPart) part).setJaxbElement((org.opendope.components.Components) o);

            } else if (o instanceof JAXBElement<?>
                && XmlUtils.unwrap(o) instanceof org.docx4j.bibliography.CTSources) {
              part = new BibliographyPart(name);
              ((BibliographyPart) part)
                  .setJaxbElement((JAXBElement<org.docx4j.bibliography.CTSources>) o);

            } else {

              log.error("TODO: handle known CustomXmlPart part  " + o.getClass().getName());

              CustomXmlDataStorage data = getCustomXmlDataStorageClass().factory();
              is.reset();
              data.setDocument(is); // Not necessarily JAXB, that's just our method name
              ((org.docx4j.openpackaging.parts.CustomXmlDataStoragePart) part).setData(data);
            }

          } catch (javax.xml.bind.UnmarshalException ue) {

            log.warn("No JAXB model for this CustomXmlDataStorage part; " + ue.getMessage());

            CustomXmlDataStorage data = getCustomXmlDataStorageClass().factory();
            is.reset();
            data.setDocument(is); // Not necessarily JAXB, that's just our method name
            ((org.docx4j.openpackaging.parts.CustomXmlDataStoragePart) part).setData(data);
          }

        } else if (part instanceof org.docx4j.openpackaging.parts.XmlPart) {

          is = partStore.loadPart(resolvedPartUri);

          //					try {
          ((XmlPart) part).setDocument(is);

          // Experimental 22/6/2011; don't fall back to binary (which we used to)

          //					} catch (Docx4JException d) {
          //						// This isn't an XML part after all,
          //						// even though ContentTypeManager detected it as such
          //						// So get it as a binary part
          //						part = getBinaryPart(partByteArrays, ctm, resolvedPartUri);
          //						log.warn("Could not parse as XML, so using BinaryPart for "
          //								+ resolvedPartUri);
          //						((BinaryPart)part).setBinaryData(is);
          //					}

        } else {
          // Shouldn't happen, since ContentTypeManagerImpl should
          // return an instance of one of the above, or throw an
          // Exception.

          log.error("No suitable part found for: " + resolvedPartUri);
          part = null;
        }

      } catch (PartUnrecognisedException e) {
        log.error("PartUnrecognisedException shouldn't happen anymore!", e);
        // Try to get it as a binary part
        part = getBinaryPart(ctm, resolvedPartUri);
        log.warn("Using BinaryPart for " + resolvedPartUri);

        //				is = partStore.loadPart( resolvedPartUri);
        //				((BinaryPart)part).setBinaryData(is);
      }
    } catch (Exception ex) {
      // IOException, URISyntaxException
      ex.printStackTrace();
      throw new Docx4JException("Failed to getPart", ex);

    } finally {
      IOUtils.closeQuietly(is);
    }

    if (part == null) {
      throw new Docx4JException(
          "cannot find part "
              + resolvedPartUri
              + " from rel "
              + rel.getId()
              + "="
              + rel.getTarget());
    }

    return part;
  }
Beispiel #16
0
  /**
   * Get a Part (except a relationships part), and all its related parts. This can be called
   * directly from outside the library, in which case the Part will not be owned by a Package until
   * the calling code makes it so.
   *
   * @param zf
   * @param source
   * @param unusedZipEntries
   * @param pkg
   * @param r
   * @param resolvedPartUri
   * @throws Docx4JException
   * @throws InvalidFormatException
   */
  private void getPart(OpcPackage pkg, RelationshipsPart rp, Relationship r, ContentTypeManager ctm)
      throws Docx4JException, InvalidFormatException, URISyntaxException {

    Base source = null;
    String resolvedPartUri = null;

    if (r.getType().equals(Namespaces.HYPERLINK)) {
      // Could be Internal or External
      // Example of Internal is w:drawing/wp:inline/wp:docPr/a:hlinkClick
      log.info("Encountered (but not loading) hyperlink " + r.getTarget());
      return;
    } else if (r.getTargetMode() == null || !r.getTargetMode().equals("External")) {

      // Usual case

      source = rp.getSourceP();
      resolvedPartUri =
          URIHelper.resolvePartUri(rp.getSourceURI(), new URI(r.getTarget())).toString();

      // Now drop leading "/'
      resolvedPartUri = resolvedPartUri.substring(1);

      // Now normalise it .. ie abc/def/../ghi
      // becomes abc/ghi
      // Maybe this isn't necessary with a zip file,
      // - ZipFile class may be smart enough to do it.
      // But it is certainly necessary in the JCR case.
      //			resolvedPartUri = (new java.net.URI(resolvedPartUri)).normalize().toString();
      //			log.info("Normalised, it is " + resolvedPartUri );

    } else {
      // EXTERNAL
      if (loadExternalTargets && r.getType().equals(Namespaces.IMAGE)) {
        // It could instead be, for example, of type hyperlink,
        // and we don't want to try to fetch that
        log.info("Loading external resource " + r.getTarget() + " of type " + r.getType());
        BinaryPart bp = ExternalResourceUtils.getExternalResource(r.getTarget());
        pkg.getExternalResources().put(bp.getExternalTarget(), bp);
      } else {
        log.info(
            "Encountered (but not loading) external resource "
                + r.getTarget()
                + " of type "
                + r.getType());
      }
      return;
    }

    String relationshipType = r.getType();
    Part part;

    if (pkg.handled.get(resolvedPartUri) != null) {

      // The source Part (or Package) might have a convenience
      // method for this
      part = pkg.getParts().getParts().get(new PartName("/" + resolvedPartUri));
      if (source.setPartShortcut(part, relationshipType)) {
        log.debug(
            "Convenience method established from "
                + source.getPartName()
                + " to "
                + part.getPartName());
      }
      return;
    }

    part = getRawPart(ctm, resolvedPartUri, r); // will throw exception if null

    // The source Part (or Package) might have a convenience
    // method for this
    if (source.setPartShortcut(part, relationshipType)) {
      log.debug(
          "Convenience method established from "
              + source.getPartName()
              + " to "
              + part.getPartName());
    }

    if (part instanceof BinaryPart || part instanceof DefaultXmlPart) {
      // The constructors of other parts should take care of this...
      part.setRelationshipType(relationshipType);
    }
    rp.loadPart(part, r);
    pkg.handled.put(resolvedPartUri, resolvedPartUri);

    //		unusedZipEntries.put(resolvedPartUri, new Boolean(false));

    RelationshipsPart rrp = getRelationshipsPart(part);
    if (rrp != null) {
      // recurse via this parts relationships, if it has any
      addPartsFromRelationships(part, rrp, ctm);
      String relPart = PartName.getRelationshipsPartName(part.getPartName().getName().substring(1));
      //			unusedZipEntries.put(relPart, new Boolean(false));
    }
  }
Beispiel #17
0
  public static void recurse(
      Alterations alterations, RelationshipsPart thisRP, RelationshipsPart otherRP)
      throws Docx4JException {

    log.info("######### @" + thisRP.partName.getName() + "#########");

    log.info("uniques -------");
    List<Relationship> uniques = thisRP.uniqueToThis(otherRP);
    addPartsForRels(alterations.getPartsAdded(), uniques, thisRP);

    List<Relationship> missings = thisRP.uniqueToOther(otherRP);
    addPartsForRels(alterations.getPartsDeleted(), missings, otherRP);

    // is this rels part itself altered?
    if (!thisRP.isContentEqual(otherRP)) {
      alterations.getPartsModified().add(new Alteration(thisRP, toStorageFormat(thisRP)));
    }

    log.info("content -------");
    List<Relationship> altered = thisRP.differingContent(otherRP);
    addPartsForRels(alterations.getPartsModified(), altered, thisRP);

    // Now recurse all rels
    log.info("recurse ------- ");
    for (Relationship r : thisRP.getJaxbElement().getRelationship()) {

      if (r.getTargetMode() != null && r.getTargetMode().equals("External")) {
        // do nothing
      } else {
        if (uniques.contains(r)) {
          // add tree, including any external parts
          // (we already have the part itself)
          addTree(alterations.getPartsAdded(), thisRP.getPart(r).getRelationshipsPart());

        } else if (missings.contains(r)) {
          addTree(alterations.getPartsDeleted(), thisRP.getPart(r).getRelationshipsPart());
        } else {
          // its present in both trees.
          // irrespective of whether content of part is the same, content of a rel could still have
          // changed
          Part thisPart = thisRP.getPart(r);
          Part otherPart =
              otherRP.getPart(RelationshipsPart.getRelationshipByTarget(otherRP, r.getTarget()));

          if (thisPart.getRelationshipsPart() == null) {

            if (otherPart.getRelationshipsPart() != null) {
              // add tree, including any external parts
              alterations
                  .getPartsDeleted()
                  .add(
                      new Alteration(
                          thisPart.getPartName(),
                          toStorageFormat(thisPart.getRelationshipsPart())));
              addTree(alterations.getPartsDeleted(), thisPart.getRelationshipsPart());
            }

          } else {

            if (otherPart.getRelationshipsPart() == null) {
              // add tree, including any external parts
              alterations
                  .getPartsAdded()
                  .add(
                      new Alteration(
                          thisPart.getPartName(),
                          toStorageFormat(thisPart.getRelationshipsPart())));
              addTree(alterations.getPartsAdded(), thisPart.getRelationshipsPart());

            } else {
              recurse(
                  alterations, thisPart.getRelationshipsPart(), otherPart.getRelationshipsPart());
            }
          }
        }
      }
    }
  }
  private WordprocessingMLPackage fetchComponents(
      WordprocessingMLPackage srcPackage, ContentAccessor contentAccessor) throws Docx4JException {

    // convert components to altChunk
    Map<Integer, CTAltChunk> replacements = new HashMap<Integer, CTAltChunk>();
    Integer index = 0;
    justGotAComponent = false;

    LinkedList<Integer> continuousBeforeIndex = new LinkedList<Integer>();
    List<Boolean> continuousBefore = new ArrayList<Boolean>();

    List<Boolean> continuousAfter = new ArrayList<Boolean>();

    for (Object block : contentAccessor.getContent()) {

      // Object ublock = XmlUtils.unwrap(block);
      if (block instanceof org.docx4j.wml.SdtBlock) {

        org.docx4j.wml.SdtBlock sdt = (org.docx4j.wml.SdtBlock) block;

        Tag tag = getSdtPr(sdt).getTag();

        if (tag == null) {
          List<Object> newContent = new ArrayList<Object>();
          newContent.add(sdt);
          continue;
        }

        log.info(tag.getVal());

        HashMap<String, String> map = QueryString.parseQueryString(tag.getVal(), true);

        String componentId = map.get(BINDING_ROLE_COMPONENT);
        if (componentId == null) continue;

        // Convert the sdt to a w:altChunk
        // .. get the IRI
        String iri = ComponentsPart.getComponentById(components, componentId).getIri();
        log.debug("Fetching " + iri);

        if (docxFetcher == null) {
          log.error("You need a docxFetcher (and the MergeDocx extension) to fetch components");
          return srcPackage;
        }

        // .. create the part
        AlternativeFormatInputPart afiPart =
            new AlternativeFormatInputPart(
                getNewPartName(
                    "/chunk", ".docx", srcPackage.getMainDocumentPart().getRelationshipsPart()));
        afiPart.setBinaryData(docxFetcher.getDocxFromIRI(iri));

        afiPart.setContentType(
            new ContentType(
                "application/vnd.openxmlformats-officedocument.wordprocessingml.document.main+xml")); // docx

        Relationship altChunkRel = srcPackage.getMainDocumentPart().addTargetPart(afiPart);
        CTAltChunk ac = Context.getWmlObjectFactory().createCTAltChunk();
        ac.setId(altChunkRel.getId());

        replacements.put(index, ac);

        /*
         * 2011 12 11 TODO.  Rethink support for
         * od:continuousBefore and od:continuousAfter.
         */

        // This is handled in this class
        if (map.get(BINDING_ROLE_COMPONENT_BEFORE) != null
            && map.get(BINDING_ROLE_COMPONENT_BEFORE).equals("true")) {
          continuousBefore.add(Boolean.TRUE);
          continuousBeforeIndex.addFirst(index);
          log.info("ctsBefore index: " + index);
        } else {
          continuousBefore.add(Boolean.FALSE);
          continuousBeforeIndex.addFirst(index);
        }

        // The following is handled in ProcessAltChunk
        if (map.get(BINDING_ROLE_COMPONENT_AFTER) != null
            && map.get(BINDING_ROLE_COMPONENT_AFTER).equals("true")) {
          continuousAfter.add(Boolean.TRUE);
        } else {
          continuousAfter.add(Boolean.TRUE);
        }

        justGotAComponent = true;
      }
      index++;
    }

    if (!justGotAComponent) {
      return srcPackage;
    }

    // Now replace in list
    for (Integer key : replacements.keySet()) {
      contentAccessor.getContent().set(key, replacements.get(key));
    }

    // Go through docx in reverse order
    List<Object> bodyChildren = contentAccessor.getContent();
    int i = 0;
    for (Integer indexIntoBody : continuousBeforeIndex) {

      if (continuousBefore.get(i)) {
        // Element before the w:altChunk
        if (indexIntoBody == 0) {
          // // Insert a sectPr right at the beginning of the docx?
          // // TODO check this isn't necessary
          // SectPr newSectPr =
          // Context.getWmlObjectFactory().createSectPr();
          // SectPr.Type type =
          // Context.getWmlObjectFactory().createSectPrType();
          // type.setVal("continuous");
          // newSectPr.setType( type );
          //
          // bodyChildren.add(0, newSectPr);

        } else {
          Object block = bodyChildren.get(indexIntoBody.intValue() - 1);
          if (block instanceof P
              && ((P) block).getPPr() != null
              && ((P) block).getPPr().getSectPr() != null) {
            makeContinuous(((P) block).getPPr().getSectPr());
          } else if (block instanceof P) {
            // More likely
            PPr ppr = ((P) block).getPPr();
            if (ppr == null) {
              ppr = Context.getWmlObjectFactory().createPPr();
              ((P) block).setPPr(ppr);
            }
            SectPr newSectPr = Context.getWmlObjectFactory().createSectPr();
            SectPr.Type type = Context.getWmlObjectFactory().createSectPrType();
            type.setVal("continuous");
            newSectPr.setType(type);

            ppr.setSectPr(newSectPr);
          } else {
            // Equally likely - its a table or something, so add a p
            P newP = Context.getWmlObjectFactory().createP();
            PPr ppr = Context.getWmlObjectFactory().createPPr();
            newP.setPPr(ppr);

            SectPr newSectPr = Context.getWmlObjectFactory().createSectPr();
            SectPr.Type type = Context.getWmlObjectFactory().createSectPrType();
            type.setVal("continuous");
            newSectPr.setType(type);
            ppr.setSectPr(newSectPr);

            bodyChildren.add(indexIntoBody.intValue(), newP); // add
            // before
            // altChunk
          }
        }
      }
      // else nothing specified, so go with normal MergeDocx behaviour

      i++;
    }

    // process altChunk
    try {
      // Use reflection, so docx4j can be built
      // by users who don't have the MergeDocx utility
      Class<?> documentBuilder = Class.forName("com.plutext.merge.ProcessAltChunk");
      // Method method = documentBuilder.getMethod("merge",
      // wmlPkgList.getClass());
      Method[] methods = documentBuilder.getMethods();
      Method processMethod = null;
      for (int j = 0; j < methods.length; j++) {
        log.debug(methods[j].getName());
        if (methods[j].getName().equals("process")) {
          processMethod = methods[j];
        }
      }
      if (processMethod == null) throw new NoSuchMethodException();
      return (WordprocessingMLPackage) processMethod.invoke(null, srcPackage);

    } catch (ClassNotFoundException e) {
      extensionMissing(e);
      justGotAComponent = false;
      return srcPackage;
      // throw new Docx4JException("Problem processing w:altChunk", e);
    } catch (NoSuchMethodException e) {
      // Degrade gracefully
      extensionMissing(e);
      justGotAComponent = false;
      return srcPackage;
      // throw new Docx4JException("Problem processing w:altChunk", e);
    } catch (Exception e) {
      throw new Docx4JException("Problem processing w:altChunk", e);
    }
  }