thilo.brandt

5 Posts

Scenario

You use the Sun ZIP API (package java.util.zip.*) and you experience some issues when working with zip files which contain special characters and / or umlauts e.g. German umlauts. So far the ZIP API comes with following restriction:

    As long as the zip files and all their entries are encoded in utf-8 you don't face any issues at all. Zip tools like Winzip or PKZip encode the file names usually in Cp437. When you work with zip files created with these tools which don't contain any entries with special characters and / or umlauts everything runs smoothly. When your zip file contains any special character your Java applications crash and you get an IllegelArgumentException.

     

    This is a known JDK bug and was already reported in the Java bug database. For further information have a look at the bug details: http://bugs.sun.com/bugdatabase/view_bug.do?bug_id=4415733 .</p>h1. Sample

    Zip file

    The sample zip file structure looks like the following and was zipped with Winzip (Cp437 encoded):

      1. test.zip
          1. test Ä
              1. ÄüÖ.txt
              2. $&.txt
          2. Äü%
              1. Üöäü.txt
    h2. Java code snippet

    The following Java code snippet unzips the test.zip (Cp437 encoded) file described above and prints out all the entry names to the console. Once the getNextEntry() is called for a zip entry which contains special characters and / or umlauts your Java applications crash with an IllegalArgumentException which is shown in the error section.

    h2. Error

    As you can see in the stack trace below the code snippet above crashes while calling the getNextEntry() method due to special characters and / or umlauts in the file name.

    h1. Solution

    Sun JDK 1.4.2

    The regular support for SUN J2SE 1.4.2 ended at October 2008. SAP and Sun did a close an agreement to enable customers to continue using and receiving support for SUN J2SE 1.4.2 beyond the regular support period. For further details have a look at following note [https://service.sap.com/sap/support/notes/1230512 | https://service.sap.com/sap/support/notes/1230512].

    h3. Prerequisites

    The solution for handling zip files with special characters and / or umlauts which is explained in the next chapters is part of the version JDK 1.4.2_22. Therefore make sure that you optain revision JDK 1.4.2_22 or higher.  

    h3. Optain latest revision of Sun JDK 1.4.2

     

    The following note <a href="https://service.sap.com/sap/support/notes/716604" target="_blank">Note 716604 - Access to Sun J2SE and recommended J2SE options</a> explains how to optain the latest revision of the Sun JDK 1.4.2 as a SAP customer.

    h3. Solution in detail

    With the JDK 1.4.2_22 Sun introduced the following two new VM parameters to deal with the encoding of zip files and to specify it as parameters. If no property is set, the behaviour is the same as before. New parameters:

      1. zip.encoding
      2. zip.altEncoding

    Make sure that you only set one of the two parameters. Setting zip.encoding or zip.altEncoding depends on your requirements. The parameter zip.encoding can only be set as VM argument. The parameter zip.altEncoding can either be directly set as VM start parameters e.g. in the NetWeaver AS Java settings via the ConfigTool or dynamically via System.setProperty(...) as shown below:

    AS VM start parameter:

    +-Dzip.altEncoding=Cp437 +
    -Dzip.encoding=UTF-8

       

      Note: Keep in mind that setting these parameters as VM start parameters in application server environments affects all other applications. When you set the parameters for an application server a server restart is required.

      Programmatically:

      System.setProperty("zip.altEncoding", "Cp437");

         

        Note: Keep in mind that setting this parameter programmatically in application server environments could also influence other running applications.

        h4. Parameter zip.encoding

        If the parameter / property zip.encoding is set, the defined encoding will be used in all cases except for jar files. In case of errors there isn't any fallback. The parameter can only be set as VM parameter as already mentioned above. If zip.encoding is set and zip.altEncoding is set as well zip.Encoding it will be ignored and not taken into account.

        h4. Parameter zip.altEncoding

        If the parameter zip.altEncoding is set, first of all utf-8 will be used and only in case of errors the alternative encoding is used as fallback. The property is read at usage time, so you can change the property at runtime as well as mentioned above. The property will only be taken into account if the zip.encoding parameter isn't set.

        h2. Sun JDK 5.0 / 6.0

        The solution explained for the Sun JDK 1.4.2 with revision 1.4.2_22 will also be made available for the JDK 5.0 and JDK 6.0. It is currently under clarification with Sun when the solution will be integrated. As a preliminary solution you can modify the class java.util.zip.ZipInputStream by yourself at your own risk. How to do this is explained in the following part.

        h3. Modifying java.util.zip.ZipInputStream

         

        Reimplement the class ZipInputStream and modify the readLOC() method of the class where the local header information of the zip archive is read and replace the line ZipEntry e = createZipEntry(getUTF8String(b, 0, len)); with the following code:

        Keep the package name java.util.zip in order to have access to protected variables and methods of other classes in the package. It is up to you whether you want to provide an alternative for the ZipInputStream e.g. a ZipInputStream2 class or whether you want to make these changes available in general for all applications which make use of ZipInputStream.

        The implementation above first of all tries to read in the file name with utf-8 encoding. If it fails the IllegalArgumentException is caught and the encoding is set to Cp437. Keep in mind that it is important to set the right encoding here.

        h3. Creating the jar file

        Export the modified class as jar file, name it e.g. fixed.zip.util.jar and copy the jar file somewhere to your file system.

        h3. Adding jar file to bootstrap

        The modified jar file has to be added in your bootclasspath. To do that you can set the following parameter as VM argument:

         

        -Xbootclasspath/p:<fullPathToTheJar e.g. c:\fixed.zip.util.jar>

        h2. JDK 7.0

        The solution explained for the Sun JDK 1.4.2 with revision 1.4.2_22 will already be part of the upcoming JDK 7.0.

        TechEd Session UP361: Getting Started Developing with the ECM Integration Layer of SAP NetWeaver

        Diving deeper into SAP NetWeaver’s new Enterprise Content Management integration layer and develop your own services and apps for your business application. Join session UP361 at SAP TechEd Phoenix or Vienna:

        http://www.sapteched.com/emea/edu_sessions/session.htm?id=424

        http://www.sapteched.com/usa/edu_sessions/session.htm?id=424 

        This session will give an introduction to the architecture and the Java APIs and SPIs of the new ECM service layer. As part of this session you will also build, deploy and configure your own sample application based on the new ECM service layer plus an JCA based SPI Connector to offer your own store as a persistency.

        To get an overview on ECM within SAP NetWeaver visit also Lecture UP101:

        http://www.sapteched.com/emea/edu_sessions/session.htm?id=426

        http://www.sapteched.com/usa/edu_sessions/session.htm?id=426

        The KM Web Service API was introduced for SAP NetWeaver 7.0 SPS 13 and offers a new possibility to connect to KM functions remotely. In this blog I will give a first impression what capabilities the new API will offer. h5. How to get the WSDL of the KM Web Services ?  Of course to get started with Web Services at all it is required to get access to the WSDL of the called Web Service. For KM Web Services you will find the WSDL description in the *Web Service Navigator* ([http://:/wsnavigator | http://:/wsnavigator]) of your SAP NetWeaver installation. h5. RepositoryFrameworkWS and IndexManagementWS - new Web Services in SAP NetWeaver ! There are two different Web Services in the SAP NetWeaver shipment which allow a remote KM access.  The *Repository Framework Web Service* (RepositoryFrameworkWS) offers basic functions like create, copy, move, rename or delete operations on documents (resources) in the KM repository framework. It is mainly designed for executing functions on top of a repository manager. You also can get navigations trees (folder hierarchies) and metadata of documents with this Web Service.  The followinging aspects of a repository manager are supported: 0.1. Lookup: This aspect covers lookup operations. Lookup operations are operations used to look up resources identified by resource identifiers in an repository. The resource identifier of a resource is the address of the resource and identifies exactly this single resource.  0.2. Namespace: This aspect covers namespace operations. Namespace operations are operations reading or manipulating the hierarchy of resources in the repository. Retrieving all child resources of a collection is an example of reading - creating a new document is an example of writing.  0.3. Property: This aspect covers property operations. Properties are bits of information attached to a resource. They have a name, are of a predefined type, e.g. boolean or string and have one or multiple values. Retrieving all properties of a resource is an example of reading - setting a new property is an example of writing.  0.4. Content: Content is stored in a byte array and only documents may have content. When a content is set, certain properties are set along with, e.g. the content length or type. Thoose properties are also available as one single object, the content metadata object. Retrieving content or content metadata is an example of reading - setting content is an example of writing.  0.5. Lock: Locking a resource helps synchronizing on resources. Different locks are available, e.g. for reading or writing and can be set or removed. Locks have a timeout in order to automatically free resources. Getting all locks on a resource is an example of reading - aquiring a lock on a resource is an example of writing.  0.6. Security: When a read or write operation on an aspect is called the caller must have certain permissions to do so, e.g. user A may read, but may not create new resources. These permissions can be queried or set using this aspect. Checking for a certain permission for a user is an example of reading - setting the permission for a certain user is an example of writing, but not yet supported.  0.7. Versioning: Resources can be set under version control, meaning that all changes to the resources can be tracked. Only checked out resources can be modified and all changes will be collected and assigned to the revision given back by the system when checking the resource in again. Querying the revision history is an example of reading - checking a resource in is an example of writing.    The *Index Management Web Service* (IndexManagementWS) offers indexing and search capabilities on top of KM's index management service.  The followinging aspects of the index management are supported: 0.1. Index: This aspect covers index management operations. It provides some basic management features to create/delete indexes and to attach/detach datasources as well as the search funtionality.  0.2. PerfIdxMgmt: This aspect covers performance issues and is needed for Web Service maintenance purposes only. Performance information supports developers in using and optimizing the Service. Among other information the processing time (on average/last call) or failure rate (number of caught exceptions in relation to number of made calls) can be queried per Web Service method.  0.3. CfgIdxMgmt: This aspect covers config operations and is needed for Web Service maintenance purposes only. Configuration settings define various runtime properties of the Web Service. Among other settings tracing or logging can thereby be switched on or off.  The following diagram will show a simplified architecture of the KM Web Services:

        A set of useful UI components bundled together.

        Since months I was ask more and more often about how to get started with Flexible UI component development in the SAP NetWeaver Developer Studio. Since there are no wizards or plugins for Flexible UI components available, developers often struggle with the project setup and the required XML configuration file. I have put together a sample SAP NetWeaver Developer Studio project, including the most requested UI components I was faced the last few months. Beside the java soruce code, also the XML file configuration is plugged in.

        Components in details...

        You will find the following components in the sample ZIP archive:
        1. Layout Controller: The sample implements a simple layout plus an own neutral control, which is required to place the sub-elements (ResourceRenderer and CollectionRenderer) in the corresponding area.
        2. Collection Renderer: This sample renders just some resource information in a grid layout.
        3. Resource Renderer: This sample renders the display name propertiy in a grid layout
        4. Property Renderer: This sample renders the VersionHistrory size in a property
        5. External UI Command: This sample renders a UI command which launches an ecternet URL.
        6. Screenflow Command: This sample renders a action on a resource with a confirmation dialogue and event handling.
        The configuration is stored in the src.config path in the PAR file. You will find a single configurable instance file (*.co.xml) for each component. image

        I want develop my own component &#150; and now ?

        Of course you simply can copy the whole project and rename the relevant folder and files on the file system. Import the renamed project to SAP NetWeaver Developer Studio.
        1. Rename the folder of the project in the filesystem
        2. Rename the project name in the .project file if you want to import it in parallel to the sample project.
        3. Adjust the project variable KMC_LIBS and possibly others you have set.
        4. Make sure you have the latest KMC library in the path of the variable KMC_LIBS
        5. Adjust the java package structure
        6. Remove all UI component samples you do not want to use
        7. Remove all configuration files of the deleted components
        8. Adjust the XML files for the new package structure
        9. Adjust the application key in IRFServiceWrapper interface
        10. Adjust ca.name and cma.name property in configArchive.properties
        So far it should work, to have the project ready for compilation and build. At the end I should not miss to mention, where the download of the sample is stored: Of course in the SDN !! Download Flexible UI components samples...

        Additional information

        Further information on Flexible UI development can be found in the following code samples: Also keep in mind the checklist we offer on http://help.sap.com and the information in the SAP NetWeaver Developer Guide. Have a good luck with the samples and let me know, if you are looking for additional information...

        Some performance hints from our project experience.

        During reviews of several custom codings of Knowledge Management Flexible UI components, I often recognized performance-impacting coding pitfalls. I’d like to show here some general improvements you should use to avoid time-consuming calls to the Knowledge Management’s repository framework (RF) within your Flexible UI components.

        Reuse of information within your component

        Having implemented UI components like collection renderers, property renderers etc, you often have to retrieve resource-related information from the RF. Most of the UI component methods already provide this information to the implementing method:
        
             public class SimplePropertyRenderer implements IModelledPropertyRenderer
        
                  public Component renderProperty(IProperty prop, IMetaName metaname, IResource r, IProxy proxy, IParameters p) throws WcmException {
                     :
                  }          
             }
        
        
        Avoid retrieving IResource objects from the RF via RepositoryFactory calls within your UI components:
        
             IResource res = ResourceFactory.getInstance().getResource(...);
             IRID rid = res.getRID();
             :
        
        
        Use the local reference to the resource object passed by the method instead.
        
             IRID rid = r.getRID(); // r is the local referenced variable
        
        
        Resource’s content and properties calls are expensive if you retrieve them always directly from the RF:
        
             IProperty p = r.getProperty(PropertyName.createDisplayName());
             // do something with p …
             p = r.getProperty(PropertyName.createLastModified());
        
        
              Try to use the IProxy or the PropertyAmalgamation mechanisme, which optimize the calles to the RF:
        
             IProperty p = proxy.getAmalgamation().getProperty(r, PropertyName.createDisplayName());
        
        
             

        Use mass calls

        If you have to process multiple objects of the RF, e.g. properties, try to use mass-calls, when ever it is possible:
        
             IPropertyNameList nl = new PropertyNameList();
             nl.add(PropertyName.createLastModified());
             nl.add(PropertyName.createLastModifiedBy());
             nl.add(PropertyName.createDisplayName()); 
             IPropertyMap propMap = proxy.getAmalgamation().getProperties(r, nl);
        
        
        Or if you have to call the RF directly use the mass-call operation of the ResourceFactory object.
        
             IRidList rl = new RidList();
             rl.add(RID.getRID("/documents/test.txt"));
             rl.add(RID.getRID("/documents/test2.txt"));
        
             IResource res = ResourceFactory.getInstance().getResources(rl, ...);
        
        

        Useful utility class ResourcePropertyAmalgamation

        The ResourcePropertyAmalgamation is located in the Java package com.sapportals.wcm.rendering.base and caches property calls against the RF. An instance can be get through the IProxy implementation:
             
             IProxy.getAmalgamation()
        
        

        Actions

        Filter Blog

        By date: